Переключение на Главную Страницу Страницы: [1] 2  ОтправитьПечать
Горячая тема (более 10 ответов) После загрузки 1С++ не работают другие компоненты (число прочтений - 5845 )
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
После загрузки 1С++ не работают другие компоненты
18. Марта 2013 :: 05:51
Печать  
После загрузки 1С++ перестают создаваться объекты из других компонентов, написанных по технологии Rainbow. Точнее сразу после загрузки 1С++ объект создается успешно РОВНО ОДИН РАЗ. После этого СоздатьОбъект выполняется без ошибки, но возвращает НеизвестныйОбъект. Не работало на моих компонентах, но для воспроизведения ошибки можно использовать и общедоступные, к примеру тот же vkloader, с помощью которого тоже пробовал загружать старую версию 1С++. Результаты везде одинаковые.

Код
Выбрать все
Если ЗагрузитьВнешнююКомпоненту(КаталогИБ()+"vkloader.dll")=0 Тогда
	Сообщить("Ошибка загрузки vkloader");
КонецЕсли;

Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик); // = ЗагрузчикВК
Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик); // = ЗагрузчикВК
Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик); // = ЗагрузчикВК

// Для версии 3.0.1.22
//Рез=Загрузчик.ЗагрузитьВК(КаталогИБ()+"1cpp.dll", "Addin.1C++=fde5ae76-00b3-4bdb-921b-d5937997b1b7");

// Для версии 3.2.3.20
Если ЗагрузитьВнешнююКомпоненту(КаталогИБ()+"1cpp.dll")=0 Тогда
	Сообщить("Ошибка загрузки 1C++");
КонецЕсли;

Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик); // = ЗагрузчикВК
Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик); // = НеизвестныйОбъект
Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик); // = НеизвестныйОбъект
 


  
Наверх
 
IP записан
 
trad
1c++ power user
1c++ donor
1c++ moderator
Отсутствует



Сообщений: 3047
Местоположение: Киров
Зарегистрирован: 23. Мая 2006
Пол: Мужской
Re: После загрузки 1С++ не работают другие компоненты
Ответ #1 - 18. Марта 2013 :: 06:34
Печать  
1cpp.dll нужно загружать самой первой
  

1&&2&&3
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #2 - 18. Марта 2013 :: 06:37
Печать  
Порядок загрузки значения не имеет. Перепробованы все варианты. Грузить первой 1С++, грузить все компоненты вначале, в середине, вперемежку. Результаты одинаковые.

Также попробовано с вкл/откл TurboBL.

Можно еще так:

Код
Выбрать все
Если ЗагрузитьВнешнююКомпоненту(КаталогИБ()+"1cpp.dll")=0 Тогда
	Сообщить("Ошибка загрузки 1C++");
КонецЕсли;
Если ЗагрузитьВнешнююКомпоненту(КаталогИБ()+"vkloader.dll")=0 Тогда
	Сообщить("Ошибка загрузки vkloader");
КонецЕсли;
Если ЗагрузитьВнешнююКомпоненту(КаталогИБ()+"test.dll")=0 Тогда
	Сообщить("Ошибка загрузки test");
КонецЕсли;

Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик+" "+ТипЗначения(Загрузчик)); // = ЗагрузчикВК 100
Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик+" "+ТипЗначения(Загрузчик)); // = НеизвестныйОбъект 100
Загрузчик=СоздатьОбъект("ЗагрузчикВК");
Сообщить("= "+Загрузчик+" "+ТипЗначения(Загрузчик)); // = НеизвестныйОбъект 100

Загрузчик=СоздатьОбъект("Тест");
Сообщить("= "+Тест+" "+ТипЗначения(Тест)); // = Тест 100
Загрузчик=СоздатьОбъект("Тест");
Сообщить("= "+Тест+" "+ТипЗначения(Тест)); // = НеизвестныйОбъект 100
Загрузчик=СоздатьОбъект("Тест");
Сообщить("= "+Тест+" "+ТипЗначения(Тест)); // = НеизвестныйОбъект 100
 



Каждый объект создается ровно один раз.

Проверено также отладчиком: при втором и последующих созданиях объекта никаких попыток вызова CreateObject не происходит.

1С++ перехватывает какие-то функции по созданию объектов? Кто знает, скажите откуда хотя бы начать копать?
  
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #3 - 18. Марта 2013 :: 07:45
Печать  
Таки-ведь нашел!
Еще как она любит все перехватывать всякими CCreateInstanceBoost.

Даже нашел как исправить: класс не реализовывал виртуальный метод GetRuntimeClass (он был в другом месте статический и просто передавался 1С, а ей этого хватало вполне), поэтому CCreateInstanceBoost ломался. После реализации этого метода все начинает работать.

Точнее CCreateInstanceBoost создает базовый объект CBLContext.
« Последняя редакция: 18. Марта 2013 :: 09:04 - dfuy »  
Наверх
 
IP записан
 
kms
1c++ power user
1c++ moderator
Отсутствует


я хочу, чтоб сюда проложили
дорогу оттуда...

Сообщений: 4632
Зарегистрирован: 19. Мая 2006
Re: После загрузки 1С++ не работают другие компоненты
Ответ #4 - 18. Марта 2013 :: 08:53
Печать  
Ну, супер, документируйте где-нибудь, какие именно изменения требуются, чтобы все было норм.
Можно исходник исправленный прикрепить сюда.
Хорошо бы еще и этот test.dll тоже с исходником, чтобы можно было проверить и убедиться.
Напишем Артуру (artbear), он давно хотел сделать что-то хорошее.
  

De quelle planète es-tu?
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #5 - 18. Марта 2013 :: 09:07
Печать  
Все сделаю в лучшем виде. Сейчас еще отлаживаю и дописываю. Там еще всякие нюансы небольшие всплывают, но я их почти уже победил. Как все заработает на 100%, сразу выложу.
  
Наверх
 
IP записан
 
trad
1c++ power user
1c++ donor
1c++ moderator
Отсутствует



Сообщений: 3047
Местоположение: Киров
Зарегистрирован: 23. Мая 2006
Пол: Мужской
Re: После загрузки 1С++ не работают другие компоненты
Ответ #6 - 18. Марта 2013 :: 10:27
Печать  
Проверил vkloader. Да, действительно, объект создается только 1 раз при загруженном 1с++.

Интересно. Вот например Formex - тоже реализован по технологии rainbow. Люди не жалуются на несовместимость с 1с++.
У меня есть куча ВК по той же, так называемой технологии rainbow. С ними тоже я проблем не наблюдаю.

ps под технологией rainbow я понимаю: линкование библиотек v7 и регистрация классов непосредственно через CBLContext::RegisterContextClass, а не по ТСВК через интерфейс LanguageExtender

pps Просто наблюдения
  

1&&2&&3
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #7 - 18. Марта 2013 :: 11:25
Печать  
to trad:
Как я уже сказал, проблема выяснена. Это особенности движка, на котором писан vkloader (изначального авторства Александра Орефкова telepat@inbox.ru). В частности не был реализован виртуальный метод GetRuntimeClass, без чего не может правильно работать CCreateInstanceBoost из 1С++.

Движок был полностью переработан. Проведена полная ревизия кода, исправлены некоторые другие потенциальные баги и еще слегка ускорена работа с объектами. Сейчас вот еще добил и GetRuntimeClass. Писать на этом движке простые компоненты очень удобно (и не в ущерб эффективности, а даже наоборот, и компилится начиная от VS6). Правда еще не закончил, планирую еще немного расширить функциональность. Но пока могу выложить текущую версию с исправленным vkloader'ом в придачу. Теперь совместим с 1С++: объекты создаются до и после ее загрузки и в любых количествах.

Каталог 1cheaders должен лежать на том же уровне, что vkloader, а Libs внутри 1cheaders.

Единственное - экспериментально отключил COneAddinImpl, ибо прекрасно грузится и без него (по крайней мере, в моих условиях). ХЗ как проверить, что везде работать будет. Хотя поставлю сегодня вечером на работе, завтра узнаем Улыбка
  

vkloader.7z ( 26 KB | Загрузки )
Наверх
 
IP записан
 
trad
1c++ power user
1c++ donor
1c++ moderator
Отсутствует



Сообщений: 3047
Местоположение: Киров
Зарегистрирован: 23. Мая 2006
Пол: Мужской
Re: После загрузки 1С++ не работают другие компоненты
Ответ #8 - 18. Марта 2013 :: 12:10
Печать  
dfuy писал(а) 18. Марта 2013 :: 11:25:
Это особенности движка, на котором писан vkloader
ты обратись к Саше. У него есть более свежий "движок" (набор шаблонов) для написания ВК. Я писал все свои ВК на нем. Проблем нет. Скорее всего он поделиться.
  

1&&2&&3
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #9 - 18. Марта 2013 :: 12:19
Печать  
trad писал(а) 18. Марта 2013 :: 12:10:
ты обратись к Саше. У него есть более свежий "движок" (набор шаблонов) для написания ВК...

нее, я чужому коду не доверяю. Собственно я его скорее не переписывал, а взял за основу и накатал свой по образу и подобию. Проблемы с 1С++ вроде решены, так что пойду щас клепать на нем тонны объектов. Столько надо с делфи перетаскивать...
  
Наверх
 
IP записан
 
trad
1c++ power user
1c++ donor
1c++ moderator
Отсутствует



Сообщений: 3047
Местоположение: Киров
Зарегистрирован: 23. Мая 2006
Пол: Мужской
Re: После загрузки 1С++ не работают другие компоненты
Ответ #10 - 18. Марта 2013 :: 12:29
Печать  
тогда нужно резюмировать, что это не проблема всех "других компонентов, написанных по технологии Rainbow", а проблема конкретно vkloader (для которого найдена правка) и компонент на основе его кода
  

1&&2&&3
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #11 - 18. Марта 2013 :: 12:38
Печать  
именно так, точнее это проблема все компонентов, которые не реализуют виртуальный метод GetRuntimeClass. Если писать через DECLARE_DYNAMIC и IMPLEMENT_DYNAMIC как по правилам, то все будет хорошо. Но если для удобства паковать это в упрощенном виде в шаблоны, нужно не забывать про вышеуказанный GetRuntimeClass (а также GetBaseClass внутри него имеет критическое значение, как показали недавние эксперименты).
  
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #12 - 18. Марта 2013 :: 23:48
Печать  
простите, забыл саму исправленную дллку в архив засунуть. Может кому пригодится.

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

vkloader_dll.7z ( 12 KB | Загрузки )
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #13 - 19. Марта 2013 :: 14:11
Печать  
Целый день работает новый vkloader, пока жалоб нет. Кстати вспомнил, что на сервере у нас с ним раньше были проблемы. 1Ска падала при его загрузке. Поэтому на серваке его вырубили (благо под амином итак все компоненты грузятся). Так что баги были не потенциальные, а вполне реальные (скорее всего это был перехват с внедрением в код функции инструкции jmp - она занимает 5 байт, а Vkloader затирал 8, а некоторые функции сами состоят из длинного jmp размером 6 байт, а за ними сразу идет другой jmp - без выравнивания почему-то - и его затирало к ебеням, сам видел когда тестил!). Сейчас внедряет ровно 5 байт. Но на серваке еще не проверял его.
  
Наверх
 
IP записан
 
dfuy
Junior Member
**
Отсутствует



Сообщений: 41
Зарегистрирован: 18. Марта 2013
Re: После загрузки 1С++ не работают другие компоненты
Ответ #14 - 19. Марта 2013 :: 14:15
Печать  
Простите за флуд, но охота излить мысли куда-нибудь. Как закончу работу над новым "движком", может выложу его куда-нибудь в отдельную тему, а пока напишу сюда.

Дак вот, прибирал я структуру Runtime классов. Поломав голову, получилось реализовать ее правильное (причем автоматическое!) формирование с помощью тех же шаблонов, даже при наследовании их друг от друга. А раз уж такое дело, стал реализовывать возможность наследования вообще (ну а че зря пропадать-то такому добру). Весь мозг вынес. Структура шаблонов усложнилась до того, что компилятор перестал компилировать код, вылетая в рандомных местах в Internal Compiler Error. А если и компилировал, то вылетала уже программа с переполнением стека (компилятор вместо вызова функции из базового типа вызывал саму себя), Acces Violation'ами и прочими прелестями. Шаманскими действиями над кодом (к примеру, вместо вызова типа SomeClass:Prev:SomeFunc() пишем метод SomeClass:PrevSomeFunc(), а он уже вызывает Prev:SomeFunc()) удалось-таки добиться правильной компиляции кода. Возможно, более новые компиляторы так издеваться над прогой не будут, так что если уж удалось скомпилить под VS6, остальные должны делать на раз.

Причем хэш-таблицы свойств для наследованных классов строятся свои и вызовов к базовым классам для поиска не перегруженных свойств не происходит. Правда таблицы при этом немного распухают, ибо на этапе компиляции невозможно выяснить, сколько в итоговой таблице окажется свойств с учетом их перекрытия, но кому сегодня жалко лишних сотню байт? Зато хэш-коллизий становится меньше Улыбка

текущая версия "движка" с наследованием:
  

contimpl.7z ( 15 KB | Загрузки )
Наверх
 
IP записан
 
Переключение на Главную Страницу Страницы: [1] 2 
ОтправитьПечать