Sfoglia il codice sorgente

Avoid race conditions in multiple load attempts.

t00thpick1 11 anni fa
parent
commit
f809bca47b

+ 15 - 0
src/main/java/com/gmail/nossr50/runnables/player/PlayerProfileLoadingTask.java

@@ -1,5 +1,7 @@
 package com.gmail.nossr50.runnables.player;
 
+import java.util.concurrent.locks.ReentrantLock;
+
 import org.bukkit.Server;
 import org.bukkit.entity.Player;
 import org.bukkit.scheduler.BukkitRunnable;
@@ -18,6 +20,8 @@ public class PlayerProfileLoadingTask extends BukkitRunnable {
     private static final int MAX_TRIES = 5;
     private final Player player;
     private int attempt = 0;
+    private ReentrantLock lock = new ReentrantLock();
+    private boolean cancelled = false;
 
     public PlayerProfileLoadingTask(Player player) {
         this.player = player;
@@ -27,10 +31,16 @@ public class PlayerProfileLoadingTask extends BukkitRunnable {
     // DO NOT MODIFY THE McMMOPLAYER FROM THIS CODE
     @Override
     public void run() {
+        lock.lock();
+        if (this.cancelled) {
+            return;
+        }
         // Quit if they logged out
         if (!player.isOnline()) {
             mcMMO.p.getLogger().info("Aborting profile loading recovery for " + player.getName() + " - player logged out");
             this.cancel();
+            cancelled  = true;
+            lock.unlock();
             return;
         }
 
@@ -46,6 +56,8 @@ public class PlayerProfileLoadingTask extends BukkitRunnable {
         if (profile.isLoaded()) {
             new ApplySuccessfulProfile(profile).runTask(mcMMO.p);
             this.cancel();
+            cancelled = true;
+            lock.unlock();
             return;
         }
 
@@ -55,8 +67,11 @@ public class PlayerProfileLoadingTask extends BukkitRunnable {
             mcMMO.p.getServer().broadcast(LocaleLoader.getString("Profile.Loading.AdminFailureNotice", player.getName() ), Server.BROADCAST_CHANNEL_ADMINISTRATIVE);
             player.sendMessage(LocaleLoader.getString("Profile.Loading.Failure").split("\n"));
             this.cancel();
+            cancelled = true;
+            lock.unlock();
             return;
         }
+        lock.unlock();
     }
 
     private class ApplySuccessfulProfile extends BukkitRunnable {