jangle писал(а):Блин как все сложно
Ладно, буду разбираться дальше.
Да в принципе ничего сложного.
_________
Мир устроен так, что что рантайм держит несколько экземпляров класса
CVBThreadAction.
Каждый экземпляр с одной стороны ассоциирован с VB-проектом (то есть exe-, dll- или ocx- модулем, подгруженным в АП процесса).
Каждый экземпляр с другой стороны связан с каким-то потоком процесса.
Всё, что нужно, чтобы код проекта X работал в контексте потока Y — создать для пары X:Y экземпляр класса
CVBThreadAction.
________ (всё!)
Создан экземпляр — всё работает. Не создан — всё падает (как попытки использовать многопоточность, так и попытки делать Native DLL, ибо причина одна).
По-моему достаточно просто.
Сложность в том, что разработчики рантайма не дали прямого документированного способа создавать такой экземпляр. Они могли написать функцию с 3 строчками кода и экспортировать её (например как rtcStartThread), и тогда в интернете можно было бы найти ни одной фразы «VB не поддерживает многопоточность». А так фраза есть, но её истинность заключается только в отсутствии этих 3 строчек кода экспортируемой функции (которых нет), на фоне тысяч строк кода реализации самой CVBThreadAction, которая и обеспечивает беспроблемную многопоточность.
Зато если мы имеем дело с ActiveX DLL или ActiveX EXE проектом, мы имеем косвенный способ заставить рантайм создать экземпляр CVBThreadAction — достаточно у проекта запросить создание экземпляра какого-нибудь внутрипроектного PublicCreatable-класса.
Со Standard EXE такой косвенной возможности нет. Поэтому я делаю кирпич: он делает только то, что для стороннего наблюдателя предоставляет ту же семантику создания потока, что и функция CreateThread, а изнутри занимается как раз тем, что делает всю необходимую работу с новым экземпляром
CVBThreadAction. Есть там и другой момент: среда в свойствах проекта лочит выбор Threading Model, поэтому переменные в Standard EXE безальтернативно всегда оказываются не потоко-специфичными. Поэтому кирпич делает ещё кое-что: использует уникальный механизм, который позволяет сделать любой уже скомпилированный чужой не-потоко-безопасный код потоко-безопасным. Да и то этот механизм нужен только для Standard EXE и только до тех пор, пока не выйдет AMC-Tools и не разлочит выбор Threading Model в режиме проекта Standard EXE.
jangle писал(а):P.S. Еще вопрос, почему происходит краш если даже закоментить в DLL вызов CallBack функции из VB? Ведь mThread_Save уже выполняется изолированно, и с VB никак не взаимодействует.
Тогда косяк у тебя. Крэш же сопровождается не грустным возгласом в голове. А вполне материальным окном, с которого можно посмотреть кучу информации и даже подключиться отладчиком.