Почему Thread.Join () зависает, хотя методы в потоке вернулись? - PullRequest
5 голосов
/ 25 ноября 2011

У меня есть приложение WPF, которое использует некоторый библиотечный код для аутентификации, которое должно выполняться в потоке однопотоковой квартиры.Мой подход заключается в создании отдельного потока для получения объекта аутентификации, блокирования до тех пор, пока поток не вернется, а затем продолжения выполнения.Тем не менее, в некоторых случаях мое приложение зависает в Thread.Join (), даже несмотря на то, что возвращен метод потока.

    public static ClaimsAuthenticationResult GetClientContextAndCookieCollection(string siteUrl, out CookieCollection cookieResult)
    {
        ClaimsAuthenticationResult authResult = new ClaimsAuthenticationResult();

        // Authentication module needs to run in single-thread apartment state because it uses
        // COM library calls where this is required
        Thread authenticationThread = new Thread(new ThreadStart(threadMethod));
        authenticationThread.SetApartmentState(ApartmentState.STA);
        authenticationThread.Start();

        // Block until thread completion
        authenticationThread.Join(); // Application hangs here

        return authResult;
    }

    private static void threadMethod() {
        // In proper application: set result. But for debugging, return immediately
        return;
    }

Я новичок в многопоточности и WPF, поэтому я мог быделать что-то глупое.Кто-нибудь видит, что здесь происходит?Для записи, я не получаю проблему, если я не устанавливаю поток в STA, но это требование.

[Редактировать: Похоже, что ошибка возникает только тогда, когда я вызываю указанный методчерез привязку проверки в представлении WPF, особенно в TextBox.Когда я вызываю тот же код в конструкторе представления, код запускается как ожидалось.Это было бы приемлемым решением, но было бы интересно узнать, что на самом деле здесь происходит.]

[Редактировать: код здесь был немного упрощен для отладки - в рабочем коде метод потока - этовнутри объекта AuthThreadWorker, который позволяет возвращать результат процесса аутентификации в объект authResult.Но эти детали, насколько я могу судить, не имеют отношения к замораживанию, поскольку замораживание происходит даже в упрощенном коде.]

1 Ответ

8 голосов
/ 28 ноября 2011

на основе вашего кода; Это выглядит так, как будто вы делаете это правильно, но поток ДЕЙСТВИТЕЛЬНО не заканчивается. Попробуйте установить точку останова в конце функции в потоке; вместо ключевого слова return (в случае, если вы выполняете какую-то обработку в выражении return, которая препятствует выходу потока), как показано на рисунке ниже enter image description here. Присвоение имени потоку с помощью authenticationThread.Name (или mthread.Name, как показано в примере) также может помочь в отладке. Если поток ДЕЙСТВИТЕЛЬНО завершен, вы должны увидеть, что «поток« Ваше имя »(0x143c) завершился с кодом 0 (0x0)». в окне вывода Visual Studio.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...