2008/02/10 - ロビー強制切断は原因不明

ロビー。1年くらい前から出ている,ロビーから落とされる現象を調査しているが,未だ原因分からず。とりあえずここにコードを載せてみる。いろいろ省略してるけど,イメージ的にはこんな感じ。ロビーのユーザ名とパスワードを管理するクラス。

public class LobbyTable
{
    Map _users = new HashMap();

    public LobbyTable()
    {
        // ファイルからユーザ名とパスワードを読み込んで_usersを初期化。
        // 実装は省略
        load();
    }

    public synchronized boolean login(String name, String password)
    {
        if(_users.get(name) == null)
        {
            _users.put(name, password);

            // ファイルにユーザ名とパスワードを書き込む
            // 実装は省略
            save();
        }
        else
        {
            if(password.equals((String)_users.get(name)))
            {
                return true;
            }
            else
            {
                return false;
            }
        }
    }

    public synchronized void changePassword(String name, String password)
    {
        _users.put(name, password);

        // ファイルにユーザ名とパスワードを書き込む
        // 実装は省略
        save();
    }
}

で,発生するエラーが以下。

java.lang.NullPointerException
   at Lobby.LobbyTable.changePassword (LobbyTable.java:91)
   …

HashMap.putの引数は2つともNULL可なのでnameとpasswordは関係ない。実際デバッグコードを入れてもNULLにはなっていない。java.util.HashMapのソースコードを見ても特にNullPointerExceptionが発生しそうなところはない。残るのは_usersがNULLの可能性だけだが…。同期処理で失敗して,っていうのが考えられそうだが,それだとsynchronizedMapを使えば解決するのかもしれない。でも原因が分からないまま変えるのも気持ち悪い。

発生確率はかなり低め。ロビーが混んでるときに起こりやすいかも知れない。Javaのすごい人からのツッコミを期待して…。

コメントする