Minor IdManager adjustments.

This commit is contained in:
MobiusDevelopment 2022-09-28 22:51:42 +00:00
parent b088b93339
commit b695f3614d
58 changed files with 1363 additions and 1740 deletions

View File

@ -215,11 +215,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -421,7 +416,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -219,11 +219,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -429,7 +424,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -219,11 +219,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -429,7 +424,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -219,11 +219,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -429,7 +424,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -221,11 +221,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -433,7 +428,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -221,11 +221,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -433,7 +428,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -222,11 +222,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -435,7 +430,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -225,11 +225,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -441,7 +436,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -227,11 +227,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -445,7 +440,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -229,11 +229,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -449,7 +444,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -231,11 +231,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -453,7 +448,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -174,11 +174,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe("IdFactory: Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
new File(Config.DATAPACK_ROOT, "data/geodata").mkdirs(); new File(Config.DATAPACK_ROOT, "data/geodata").mkdirs();
@ -388,7 +383,7 @@ public class GameServer
printSection("Game Server"); printSection("Game Server");
LOGGER.info("IdFactory: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdFactory: Free ObjectID's remaining: " + IdManager.getInstance().size());
if (Config.ALLOW_WEDDING) if (Config.ALLOW_WEDDING)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -57,10 +56,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -162,13 +160,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -176,7 +178,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -187,74 +188,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -266,16 +263,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -178,11 +178,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe("IdFactory: Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
new File(Config.DATAPACK_ROOT, "data/geodata").mkdirs(); new File(Config.DATAPACK_ROOT, "data/geodata").mkdirs();
@ -400,7 +395,7 @@ public class GameServer
printSection("Game Server"); printSection("Game Server");
LOGGER.info("IdFactory: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdFactory: Free ObjectID's remaining: " + IdManager.getInstance().size());
if (Config.ALLOW_WEDDING) if (Config.ALLOW_WEDDING)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -57,10 +56,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -163,13 +161,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -177,7 +179,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -188,74 +189,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -267,16 +264,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -202,11 +202,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -403,7 +398,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -210,13 +208,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -224,7 +226,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -235,74 +236,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -314,16 +311,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -215,11 +215,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -433,7 +428,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -215,13 +213,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -229,7 +231,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -240,74 +241,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -319,16 +316,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -216,11 +216,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -435,7 +430,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -214,13 +212,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -228,7 +230,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -239,74 +240,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -318,16 +315,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -211,11 +211,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -416,7 +411,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -215,11 +215,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -424,7 +419,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -218,11 +218,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -430,7 +425,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -218,11 +218,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -430,7 +425,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -219,11 +219,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -432,7 +427,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -220,11 +220,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -434,7 +429,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -222,11 +222,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -438,7 +433,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -221,11 +221,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -436,7 +431,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -224,11 +224,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -442,7 +437,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -216,11 +216,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -426,7 +421,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -195,13 +193,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -209,7 +211,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -220,74 +221,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -299,16 +296,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -234,11 +234,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -462,7 +457,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -239,11 +239,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -472,7 +467,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;

View File

@ -243,11 +243,6 @@ public class GameServer
printSection("IdManager"); printSection("IdManager");
IdManager.getInstance(); IdManager.getInstance();
if (!IdManager.hasInitialized())
{
LOGGER.severe(getClass().getSimpleName() + ": Could not read object IDs from database. Please check your configuration.");
throw new Exception("Could not initialize the ID factory!");
}
printSection("Scripting Engine"); printSection("Scripting Engine");
EventDispatcher.getInstance(); EventDispatcher.getInstance();
@ -480,7 +475,7 @@ public class GameServer
Runtime.getRuntime().addShutdownHook(Shutdown.getInstance()); Runtime.getRuntime().addShutdownHook(Shutdown.getInstance());
LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.size()); LOGGER.info("IdManager: Free ObjectID's remaining: " + IdManager.getInstance().size());
if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS) if ((Config.OFFLINE_TRADE_ENABLE || Config.OFFLINE_CRAFT_ENABLE) && Config.RESTORE_OFFLINERS)
{ {

View File

@ -22,7 +22,6 @@ import java.sql.ResultSet;
import java.sql.Statement; import java.sql.Statement;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.BitSet; import java.util.BitSet;
import java.util.Collections;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger; import java.util.logging.Logger;
@ -60,10 +59,9 @@ public class IdManager
private static final int LAST_OID = 0x7FFFFFFF; private static final int LAST_OID = 0x7FFFFFFF;
private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID; private static final int FREE_OBJECT_ID_SIZE = LAST_OID - FIRST_OID;
private static BitSet _freeIds; private BitSet _freeIds;
private static AtomicInteger _freeIdCount; private AtomicInteger _freeIdCount;
private static AtomicInteger _nextFreeId; private AtomicInteger _nextFreeId;
private static boolean _initialized;
public IdManager() public IdManager()
{ {
@ -196,13 +194,17 @@ public class IdManager
try (Connection con = DatabaseFactory.getConnection(); try (Connection con = DatabaseFactory.getConnection();
Statement statement = con.createStatement()) Statement statement = con.createStatement())
{ {
String extractUsedObjectIdsQuery = ""; final StringBuilder extractUsedObjectIdsQuery = new StringBuilder();
for (String[] tblClmn : ID_EXTRACTS) for (String[] tblClmn : ID_EXTRACTS)
{ {
extractUsedObjectIdsQuery += "SELECT " + tblClmn[1] + " FROM " + tblClmn[0] + " UNION "; extractUsedObjectIdsQuery.append("SELECT ");
extractUsedObjectIdsQuery.append(tblClmn[1]);
extractUsedObjectIdsQuery.append(" FROM ");
extractUsedObjectIdsQuery.append(tblClmn[0]);
extractUsedObjectIdsQuery.append(" UNION ");
} }
extractUsedObjectIdsQuery = extractUsedObjectIdsQuery.substring(0, extractUsedObjectIdsQuery.length() - 7); // Remove the last " UNION " extractUsedObjectIdsQuery.setLength(Math.max(extractUsedObjectIdsQuery.length() - 7, 0)); // Remove the last " UNION "
try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery)) try (ResultSet result = statement.executeQuery(extractUsedObjectIdsQuery.toString()))
{ {
while (result.next()) while (result.next())
{ {
@ -210,7 +212,6 @@ public class IdManager
} }
} }
} }
Collections.sort(usedIds);
// Register used ids. // Register used ids.
for (int usedObjectId : usedIds) for (int usedObjectId : usedIds)
@ -221,74 +222,70 @@ public class IdManager
LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID); LOGGER.warning("IdManager: Object ID " + usedObjectId + " in DB is less than minimum ID of " + FIRST_OID);
continue; continue;
} }
_freeIds.set(usedObjectId - FIRST_OID); _freeIds.set(objectId);
_freeIdCount.decrementAndGet(); _freeIdCount.decrementAndGet();
} }
_nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0)); _nextFreeId = new AtomicInteger(_freeIds.nextClearBit(0));
_initialized = true;
} }
catch (Exception e) catch (Exception e)
{ {
_initialized = false;
LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage()); LOGGER.severe("IdManager: Could not be initialized properly: " + e.getMessage());
} }
// Schedule increase capacity task. // Schedule increase capacity task.
ThreadPool.scheduleAtFixedRate(() -> ThreadPool.scheduleAtFixedRate(() ->
{ {
synchronized (_nextFreeId) if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size())
{ {
if (PrimeFinder.nextPrime((usedIdCount() * 11) / 10) > _freeIds.size()) increaseBitSetCapacity();
{
increaseBitSetCapacity();
}
} }
}, 30000, 30000); }, 30000, 30000);
LOGGER.info("IdManager: " + _freeIds.size() + " id's available."); LOGGER.info("IdManager: " + _freeIds.size() + " id's available.");
} }
public void releaseId(int objectId) public synchronized void releaseId(int objectId)
{ {
synchronized (_nextFreeId) if ((objectId - FIRST_OID) > -1)
{ {
if ((objectId - FIRST_OID) > -1) _freeIds.clear(objectId - FIRST_OID);
_freeIdCount.incrementAndGet();
}
else
{
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")");
}
}
public synchronized int getNextId()
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
int nextFree = _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
nextFree = _freeIds.nextClearBit(0);
}
if (nextFree < 0)
{
if (_freeIds.size() < FREE_OBJECT_ID_SIZE)
{ {
_freeIds.clear(objectId - FIRST_OID); increaseBitSetCapacity();
_freeIdCount.incrementAndGet();
} }
else else
{ {
LOGGER.warning("IdManager: Release objectID " + objectId + " failed (< " + FIRST_OID + ")"); throw new NullPointerException("IdManager: Ran out of valid ids.");
} }
} }
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
} }
public int getNextId() private synchronized void increaseBitSetCapacity()
{
synchronized (_nextFreeId)
{
final int newId = _nextFreeId.get();
_freeIds.set(newId);
_freeIdCount.decrementAndGet();
final int nextFree = _freeIds.nextClearBit(newId) < 0 ? _freeIds.nextClearBit(0) : _freeIds.nextClearBit(newId);
if (nextFree < 0)
{
if (_freeIds.size() >= FREE_OBJECT_ID_SIZE)
{
throw new NullPointerException("IdManager: Ran out of valid ids.");
}
increaseBitSetCapacity();
}
_nextFreeId.set(nextFree);
return newId + FIRST_OID;
}
}
private void increaseBitSetCapacity()
{ {
final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10)); final BitSet newBitSet = new BitSet(PrimeFinder.nextPrime((usedIdCount() * 11) / 10));
newBitSet.or(_freeIds); newBitSet.or(_freeIds);
@ -300,16 +297,11 @@ public class IdManager
return _freeIdCount.get() - FIRST_OID; return _freeIdCount.get() - FIRST_OID;
} }
public static int size() public int size()
{ {
return _freeIdCount.get(); return _freeIdCount.get();
} }
public static boolean hasInitialized()
{
return _initialized;
}
public static IdManager getInstance() public static IdManager getInstance()
{ {
return SingletonHolder.INSTANCE; return SingletonHolder.INSTANCE;