tlssetvalue не сохраняет значение
От: Vitas1  
Дата: 08.06.11 08:47
Оценка:
Добрый день. Есть необходимость поработать с thread local storage в DLL, которая реализует callback-функции для стороннего приложения. Взял пример из MSDN:


// The DLL code

#include <windows.h>

static DWORD dwTlsIndex; // address of shared memory
 
// DllMain() is the entry-point function for this DLL. 
 
BOOL WINAPI DllMain(HINSTANCE hinstDLL, // DLL module handle
    DWORD fdwReason,                    // reason called
    LPVOID lpvReserved)                 // reserved
{ 
    LPVOID lpvData; 
    BOOL fIgnore; 
 
    switch (fdwReason) 
    { 
        // The DLL is loading due to process 
        // initialization or a call to LoadLibrary. 
 
        case DLL_PROCESS_ATTACH: 
 
            // Allocate a TLS index.
 
            if ((dwTlsIndex = TlsAlloc()) == TLS_OUT_OF_INDEXES) 
                return FALSE; 
 
            // No break: Initialize the index for first thread.
 
        // The attached process creates a new thread. 
 
        case DLL_THREAD_ATTACH: 
 
            // Initialize the TLS index for this thread.
 
            lpvData = (LPVOID) LocalAlloc(LPTR, 256); 
            if (lpvData != NULL) 
                fIgnore = TlsSetValue(dwTlsIndex, lpvData); 
 
            break; 
// И так далее...


Так вот, при первом вызове из потока ф-ция TlsGetValue(dwTlsIndex) всегда возвращает NULL. Если снова вызвать TlsSetValue (уже в теле потока), то все начинает работать нормально. Другими словами — куда пропал указатель lpvData, изначально сохраненный в функции DLLMain? Или так и должно быть? Или я где-то туплю?
Заранее спасибо за ответы.
Re: tlssetvalue не сохраняет значение
От: ononim  
Дата: 08.06.11 09:10
Оценка:
V>Так вот, при первом вызове из потока ф-ция TlsGetValue(dwTlsIndex) всегда возвращает NULL. Если снова вызвать TlsSetValue (уже в теле потока), то все начинает работать нормально. Другими словами — куда пропал указатель lpvData, изначально сохраненный в функции DLLMain? Или так и должно быть? Или я где-то туплю?
V>Заранее спасибо за ответы.
1) поток, который выделен в тексте, является ли тем потоком, который загрузил dll?
если ответ на вопрос 1) — "нет" — то другой вопрос: 2) поток, который выделен в тексте, запущен ли он после загрузки dll?
если ответ на вопросы 1) и 2) — нет — то так и должно быть, ибо ни DLL_PROCESS_ATTACH ни DLL_THREAD_ATTACH не приходят для других потоков приложения, которые стартовали до загрузки длл.
Как много веселых ребят, и все делают велосипед...
Re[2]: tlssetvalue не сохраняет значение
От: Vitas1  
Дата: 08.06.11 09:34
Оценка:
Здравствуйте, ononim, Вы писали:

O>1) поток, который выделен в тексте, является ли тем потоком, который загрузил dll?

O>если ответ на вопрос 1) — "нет" — то другой вопрос: 2) поток, который выделен в тексте, запущен ли он после загрузки dll?
O>если ответ на вопросы 1) и 2) — нет — то так и должно быть, ибо ни DLL_PROCESS_ATTACH ни DLL_THREAD_ATTACH не приходят для других потоков приложения, которые стартовали до загрузки длл.

1) "Да" — если судить по ID потока. Хотя допускаю, что ID может быть использован повторно другим потоком. Впрочем, я смотрел — THREAD_DETACH для потока не приходит (по крайней мере, между вызовами TlsSetValue и TlsGetValue). Получается, что изначальный поток "жестко" убивают, а его ID "быстренько" начинает юзать какой-то новый поток? Это уж совсем как-то криво...
Хотя приложение чужое, поэтому тонкости его работы, увы, сообщить не могу...
Re[3]: tlssetvalue не сохраняет значение
От: ononim  
Дата: 08.06.11 10:22
Оценка:
V>1) "Да" — если судить по ID потока. Хотя допускаю, что ID может быть использован повторно другим потоком. Впрочем, я смотрел — THREAD_DETACH для потока не приходит (по крайней мере, между вызовами TlsSetValue и TlsGetValue). Получается, что изначальный поток "жестко" убивают, а его ID "быстренько" начинает юзать какой-то новый поток? Это уж совсем как-то криво...
V>Хотя приложение чужое, поэтому тонкости его работы, увы, сообщить не могу...
Дебажить надо, таких проблем с TLS сроду не видел.
Как много веселых ребят, и все делают велосипед...
Re[4]: tlssetvalue не сохраняет значение
От: Vitas1  
Дата: 09.06.11 11:17
Оценка:
Здравствуйте, ononim, Вы писали:

V>>1) "Да" — если судить по ID потока. Хотя допускаю, что ID может быть использован повторно другим потоком. Впрочем, я смотрел — THREAD_DETACH для потока не приходит (по крайней мере, между вызовами TlsSetValue и TlsGetValue). Получается, что изначальный поток "жестко" убивают, а его ID "быстренько" начинает юзать какой-то новый поток? Это уж совсем как-то криво...

V>>Хотя приложение чужое, поэтому тонкости его работы, увы, сообщить не могу...
O>Дебажить надо, таких проблем с TLS сроду не видел.
Разобрался с помощью дебага — допустил типичную ламерскую ошибку . Статическую переменную TlsIndex я необдуманно перенес (и на фиг забыл про это) из dllmain.cpp в stdafx.h — что вызвало ее размножение по разным cpp-файлам...
Спасибо за помощь и пардон за тупость — ушел перечитывать теорию )
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.