Различие между традиционным DLL и COM DLL

Я в настоящее время изучаю COM. Я нашел, что COM DLL отчасти создается на традиционной инфраструктуре DLL. Когда мы создаем COM DLL, мы все еще полагаемся на традиционные методы экспорта DLL для продвижения нас к внутренним co-классам COM.

Если COM для многократного использования компонента на двоичном уровне, я думаю, что традиционный DLL может достигнуть того же самого. Они оба выставляют функции, они являются оба двоичными, таким образом, какой смысл того, чтобы обратиться к подходу COM?

В настоящее время у меня есть чувство, что традиционный DLL выставляет методы "плоским" способом, в то время как COM DLL выставляет методы способом иерархии "ООП". И способ ООП, кажется, лучший подход. Это могло быть причиной, почему COM преобладает?

Большое спасибо.

28
задан smwikipedia 10 June 2010 в 17:12
поделиться

8 ответов

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

Вы не получите этого, открывая свои собственные функции напрямую. Скорее всего, это можно будет использовать только из программы, написанной на C / C ++ (чтобы она могла читать ваши файлы заголовков), скомпилированной с той же версией компилятора C ++ и без проблем с взаимодействием всех видов. Такие простые вещи, как раскрытие объекта класса C ++, такого как std :: string, небезопасно.Ни компоновка памяти, ни протокол владения памятью не гарантированно совместимы.

Это могло быть больше ООП, COM не поддерживает наследование, потому что ООП очень сложно добиться совместимости на двоичном уровне. Эта проблема требует поддержки среды выполнения, в которую входит весь код, таких виртуальных машин, как .NET и Java.

34
ответ дан 28 November 2019 в 02:35
поделиться

COM DLL - это просто DLL с Com-специфическими точками входа. COM раскрывает фабрики классов для создания объектов com, поэтому должен быть способ получения доступа к одной из фабрик классов, реализованных сервером COM. Именно это и делает DllGetClassObject. Кроме того, COM DLL являются саморегистрирующимися: они могут уведомлять Windows о своих доступных классах и интерфейсах. Точкой входа для того, чтобы DLL зарегистрировала себя, является DllRegisterServer.

Есть еще несколько точек входа, но они имеют следующий вид.

Если бы не было четко определенной точки входа для DllRegisterServer, то клиенты не смогли бы заставить DLL саморегистрироваться. Это усложнило бы установку COM-компонентов.

Если бы не было стандартизированной точки входа для получения фабрик классов, то каждая DLL должна была бы определить свою собственную точку входа, и эту информацию нужно было бы внести в реестр Windows, чтобы инфраструктура COM знала, как получить доступ к фабрике классов каждой DLL. Дополнительная сложность не оправдана, поэтому эта точка входа также стандартизирована.

Что касается того, чем COM отличается от 'C', то главное отличие заключается в концепции контрактов. COM поощряет программистов мыслить в терминах абстрактных интерфейсов между модулями, а не иерархической, нисходящей декомпозиции функциональности. Это один из видов "ООП", но этот термин слишком свободен, чтобы быть полезным, IMO. Преимущества контрактно-ориентированного подхода многообразны для сильно типизированных, статически связанных языков, таких как C/C++.

15
ответ дан 28 November 2019 в 02:35
поделиться

Если вы хотите узнать о причинах внедрения COM и его философии, я настоятельно рекомендую прочитать От CPP к COM

5
ответ дан 28 November 2019 в 02:35
поделиться

Думаю, прочитав первую главу ] Essential COM вы хорошо поймете, зачем использовать COM.

Проще говоря, COM обеспечивает совместимость на двоичном уровне, независимо от того, какой язык вы использовали, какую версию компилятора вы использовали. Речь идет не об "ООП", вы наверняка можете раскрыть класс C ++ из DLL, но они не "двоично-совместимы".

8
ответ дан 28 November 2019 в 02:35
поделиться

Ключевое отличие состоит в том, что COM обеспечивает двоичную совместимость.

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

COM представил концепцию интерфейсов, которые являются неизменяемыми, поэтому не должны изменяться между сборками и т. Д. Каждый COM-объект должен реализовывать интерфейс IUnknown, который содержит метод QueryInterface, который используется для запроса у объекта указателей на другие поддерживаемые интерфейсы.

Спецификация COM гарантирует, что интерфейс IUnknown всегда находится в одном и том же месте в DLL, поэтому даже если объект изменен для поддержки большего количества интерфейсов, метод QueryInterface все равно можно будет безопасно вызывать.

5
ответ дан 28 November 2019 в 02:35
поделиться

Лучший способ представить себе COM - это представить его как контракт между вами и человеком, использующим созданный вами объект.

COM обрабатывает

  1. , как версировать ваш объект в разных выпусках
  2. , как обнаруживать ваш объект, даже если ваш объект находится в DLL, которая переименовывается или пришла из другого источника
  3. как ссылаться и уничтожать ваши объект (в отношении кучи)
  4. , как вы ожидаете, что потоки будут работать, и правила, связанные с потоками / блокировками для вашего объекта

, COM стал стандартом, потому что, хотя вы можете создать традиционную DLL, которая обрабатывает каждый из вышеперечисленных элементов вам нужно будет сформулировать ожидаемый контракт при отправке вашей DLL

, используя правила COM, эта формулировка сделана для вас

, вы также правы, что COM предоставляет объекты, в то время как более традиционные DLLS просто предоставляют функции. вы часто будете видеть, как разработчики пытаются имитировать контракты, найденные в COM на прямом C, обычно вы увидите, что они клонируют аспекты COM в их DLL (например, вы увидите методы, возвращающие структуры указателей на функции) ... опыт показывает, что если вы не используете COM для создания общедоступной DLL, вы увеличиваете вероятность пропуска некоторых случаев, особенно когда на картинке присутствует управление версиями

4
ответ дан 28 November 2019 в 02:35
поделиться

В дополнение к уже опубликованным ответам, интерфейсы COM предоставляют объекты двоичных данных независимым от языка программирования способом, что позволяет выделить память для этих объектов в одном адресном пространстве процесса и освободить в другом. Маршаллинг и демаршаллинг поиска.

Это также позволяет передавать строки, не обращая внимания на детали кодирования, чтобы определить, где может быть нулевой терминатор. COM-строки считаются строками UNICODE.

Добавьте IDL и скомпилируйте библиотеку типов в DLL, и вы получите интерфейсы с самоописанием. С обычными библиотеками DLL вы должны знать из внешних документов, какие у них есть методы и какие параметры они принимают.

Стандарт COM также может быть кроссплатформенным. Версии Office для Mac поддерживают COM, и были реализации для Unix и Unix-подобных систем, хотя они никогда не были популярны.

3
ответ дан 28 November 2019 в 02:35
поделиться

DLL имеет множество применений в windows. Многие типы библиотечного кода хранятся в DLL. Одним из них, например, являются сборки .net, а это совсем другой зверь.

COM DLL не лучше, чем "простая бинарная PE DLL", потому что COM DLL - это тоже простая DLL. Что превращает DLL в COM DLL, так это раскрытие, возможно в дополнение к другим вещам, определенных экспортов, соответствующих определенному контракту (сигнатуре) [lookup entry IUnknown], или даже нескольких типов канонизированных интерфейсов [lookup entry 'dual interface'], которые позволяют не только инстанцировать определенные объекты внутри DLL, но и автоматически обнаруживать сервисы, включая имена функций и типы параметров.

Двойные интерфейсы делают его очень удобным для связи с языками сценариев (используемыми в веб, сценариях оболочки, образовательных программах и т.д.), поскольку программисты сценариев не заботятся о строгой типизации. Двойной интерфейс, раскрываемый COM DLL, позволяет среде выполнения сценариев запрашивать, какие именно типы она ожидает, и делать соответствующие преобразования, без проблем для пользователя.

Эта гибкость позволила создать целую гигантскую инфраструктуру COM, включая регистрацию компонентов, DCOM (вызов по сети) и т.д. Это сделало довольно удобным предоставление COM-интерфейсов в компоненты windows (WMI, например) и офисные компоненты. Многие другие популярные интерфейсы были реализованы поверх COM, такие как ADO.

Все это хорошо, но COM не "преобладает" ни в каком смысле. COM DLL - это меньшинство DLL. Обычные DLL и .NET DLL очень популярны. Microsoft считает, что интерфейсы .NET превосходят COM. Многие unix-фрики и другие считают DLL вообще плохой идеей, поскольку они не предоставляют услуги связывания во время выполнения в том же смысле, что и общие объекты в unix. Несмотря на то, что я являюсь разработчиком windows, я также считаю, что SO обеспечивают превосходную альтернативу, и я надеюсь, что однажды они появятся.

5
ответ дан 28 November 2019 в 02:35
поделиться
Другие вопросы по тегам:

Похожие вопросы: