Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Основная";
Текущий архив: 2004.12.05;
Скачать: [xml.tar.bz2];

Вниз

Эта проблемная многопоточность   Найти похожие ветки 

 
Vilux ©   (2004-11-22 09:59) [0]

Создаю много потоков и в каждом потоке подключаю dll функцией
 hinstDLL := LoadLibrary(pchar(dllname));
И пишу логи. В логах видно, что в каждом потоке hinstDLL имеет одно и то же значение... так и должно быть? Дело в том, что моя программа вылетает, когда одновременно в потоках пытается подключиться dll-ка и вызваться процедура из нее... но если в каждом потоке подключать dll-ку через Synchronize, то прога не вылетает. Но зато очень медленно. Такое впечатление, что использование SYnchronize отменяет весь эффект многопоточности. Как быть? Как мне в потоках отркывать одновременно одну dll-ку и чтобы без вылетов?


 
Reindeer Moss Eater ©   (2004-11-22 10:05) [1]

У тебя ошибка в программе


 
Vilux ©   (2004-11-22 10:17) [2]

Reindeer Moss Eater, а конкретнее? Почему ты так решил?


 
Reindeer Moss Eater ©   (2004-11-22 10:21) [3]

Мне интуиция и здравый смысл это подсказывают.
А так же личный опыт.


 
Digitman ©   (2004-11-22 10:32) [4]


> в каждом потоке hinstDLL имеет одно и то же значение...
> так и должно быть?


да


> использование SYnchronize отменяет весь эффект многопоточности


на то Synchronize и нужен


 
ggs   (2004-11-22 10:32) [5]


> hinstDLL имеет одно и то же значение... так и должно быть?

Да, DLL проецируется на адресное пространство твоего процесса,
а hinstDLL и есть это адрес.


> Дело в том, что моя программа вылетает, когда одновременно
> в потоках пытается подключиться dll-ка и вызваться процедура
> из нее...

ХЗ... возможно один поток вызывает FreeLibrary а потом вытается
использовать функцию из DLL, в общем "ошибка в программе" ;)


> Такое впечатление, что использование SYnchronize отменяет
> весь эффект многопоточности.

Не совсем так... посмотри реализацию Synchronize в VCL.


> Как быть?

Загружай/выгружай DLL в основном потоке, а в рабочих используй
GetModuleHandle(Ex)...


 
Vilux ©   (2004-11-22 10:33) [6]

ПРовел еще один тест... если dll-ка пустая, то все работает*(т.е. из кучи потоков запускается без проблем). А если я там какие-нибудь переменные ввожу и все, больше ничего, никаких процедур не вызываю, ничего... то тогда прога вылетает...просто исчезает.


 
Reindeer Moss Eater ©   (2004-11-22 10:36) [7]

Тебе ж говорят, что у тебя ошибка в программе.


 
TUser ©   (2004-11-22 10:37) [8]


> если в каждом потоке подключать dll-ку через Synchronize,
> то прога не вылетает. Но зато очень медленно. Такое впечатление,
> что использование SYnchronize отменяет весь эффект многопоточности

S выполняет код от имени главного потока приложения. Так что все выполняется в одном потоке, а подгрузка dll - дело действительно довольно медленное. С другой стороны, оно хоть и медленное, но обычно однократное - подгрузили и работаем, так что заметных тормозов быть не должно. А вот если ты ее подгружаешь много раз (ты ведь создаешь много потоков) - то действительно может тормозить.
Судя по тому, что хендл везде получется один и тот же, ты грузишь одну и ту же библиотеку - а она грузится в адресное пространство процесса, причем один раз. Но попыток загрузить ее получется много, причем все в контексте главного потока. А это плохо.
Непонятно - почему бы не загрузить dll один раз в главном потоке и передать всем остальным потокам ее хендл.

PS. На этом форуме переодиечски появляются вопросы про много потоков - часто оказывается, что их так много и не надо. Опиши свою задачу, много потоков реально необходимо для очень небольшого количества задач, таких как обслуживание многих пользователей на крутых серверах и т.д.


 
Vilux ©   (2004-11-23 14:13) [9]

Описываю задачу...
есть сервер, который получает данные на вход и запускает поток. В этом потоке в зависимости от полученных данных пускается определенная dll-ка, которая работает с БД(Access) через ADO-компоненты. Нужно, чтобы все это работало быстро. Как я выяснил, прога виснет, когда создается много потоков и каждый поток через функцию dll пытается работать с БД. Т.е. мне надо, чтобы в каждом потоке подргужалась dll-ка в новую область памяти. А то получается, что я в потоках подгружаю dll и думаю, что и функции из нее в каждом потоке расположены по разным адресам, а оказывается, что все потоки одновременно обращаются к функции по одному и тому же адресу(судя по тому, что hinstdll везде одинаков), отсюда походу и идут все косяки


 
Alexander Panov ©   (2004-11-23 14:16) [10]

Vilux ©   (23.11.04 14:13) [9]

DLL загружается в твой процесс, а не в поток, и в любом потоке адрес будет одинаков.


 
Vilux ©   (2004-11-23 14:25) [11]

я уже понял, так как мне тогда решить мою проблему? чтобы не было конфликтов между потоками...


 
Alexander Panov ©   (2004-11-23 14:28) [12]

Vilux ©   (23.11.04 14:25) [11]
я уже понял, так как мне тогда решить мою проблему? чтобы не было конфликтов между потоками...


Так это не проблема.
Вот только неизвестно, в чем она у тебя - кода-то никто до сих пор не увидел.


 
sniknik ©   (2004-11-23 14:30) [13]

может убрать их? и сделать на ассинхронных запросах (выполнение в потоках внутри ADO).
и dll возможено не нужна вовсе...


 
Vilux ©   (2004-11-23 14:30) [14]

ну... я думал проблема в том, что потоки пытаются одновременно вызвать функцию, которая расположена по одному и тому же адресу. Или не так?


 
Vilux ©   (2004-11-23 14:32) [15]

dll нужна по-любому, это позволяет наращивать модульность программы. Т.е. написал новую dll и просто указал программе в каком случае ее запускать. При этом не придется трогать исходники самой программы


 
Alexander Panov ©   (2004-11-23 14:54) [16]

Vilux ©   (23.11.04 14:32) [15]
По поводу одинх и тех же адресов:
http://delphimaster.net/view/1-1101141727/


 
Alexander Panov ©   (2004-11-23 14:56) [17]

Vilux ©   (23.11.04 14:32) [15]
Вот это что -http://delphimaster.net/view/1-1101141727/ ?

Нехорошо спамом заниматься.


 
TUser ©   (2004-11-23 15:02) [18]


> Vilux ©   (23.11.04 14:13) [9]

Ты точно уверен, что тормоза возникают на подгрузке dll, а не от того, что сервер базы данных не может обрабатывать много запросов?

В любом случае, я бы сделал загрузку dll только один раз. И флаг какой-нибудь, типа "dll загружена". Тогда потоки ничего грузить пытаться не будут, а будут просто получать готовый хендл.


 
Digitman ©   (2004-11-23 15:03) [19]


> Vilux ©   (23.11.04 14:32) [15]
> dll нужна по-любому, это позволяет наращивать модульность
> программы


гадиматья.
механизм динамически линкуемых библиотек был придуман и реализован отнюдь не для этого



Страницы: 1 вся ветка

Форум: "Основная";
Текущий архив: 2004.12.05;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.52 MB
Время: 0.036 c
3-1099560939
Kat
2004-11-04 12:35
2004.12.05
Если затем открыть запрос надо ли делать IBQuery.SQL.Clear ?


1-1100970808
ЛёхА
2004-11-20 20:13
2004.12.05
Радактор кода


1-1100933147
Rocket
2004-11-20 09:45
2004.12.05
Проблема NUXI (преобразование endian)


14-1100534465
vasilii
2004-11-15 19:01
2004.12.05
profiler для Delphi7


3-1099553813
Брат
2004-11-04 10:36
2004.12.05
Создание хранимой процедуры программно





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский