1994年、OCXもしくはOLEコントロールがVBXコントロールの後継として紹介される。それと同時に、OLEは、もはや単なる頭文字ではなく、コンポーネント技術を表す用語となった。1996年初頭、マイクロソフトは、OLEのうちでインターネットと関連のあるいくつかの技術をActiveXとして名称変更した。OLEとして公開されていた技術がActiveXに統合され始める。関連技術編集COMはWindowsで主要なソフトウェア開発プラットフォームであり、数多くの技術の開発に影響を与えた。2000でのCOMの重要な拡張は(MTSによる外部ツールの組み合わせとは対照的に)OSへ統合することであり、これをCOM+と改名した。この時点でマイクロソフトは個別の要素としてDCOMを重視していなかった。COM+の追加レイヤでトランザクショナルCOMコンポーネントを直接的に取り扱った。COM+コンポーネントはコンポーネントサービスアプリケーションインタフェースを通じて追加された。farms)」で動作できる利点があった。コードが正しい場合、コンポーネントはメモリからアンロードすることなく初期化ルーチンを新たに呼び出すことにより再利用できた。以前はDCOMだけで可能だったコンポーネントの分散化(他のマシンからの呼び出し)も可能となった。Componentsというコンポーネントを介するモデルを提供した。これにより、COM+プログラミングモデルでは、遅延バインディングされたイベント、および、パブリッシャー/サブスクライバとイベントシステムの間のメソッド呼び出しがサポートされる。Frameworkに大幅に取って代わられ、マイクロソフトは.NETに注力する戦略に集中している。BasicやASPで実装されたフロントエンドのコードと接続するためによく利用されていた。好感されている.NETに対して、COMはある程度批判されている。.NET、C++/CLIを含むあらゆる.NET言語で実装できる。それでもCOMはまだ様々なテクノロジーで重要なソフトウェアの基盤として生き延びている。マルチメディアAPIとして広く普及しているDirectXのAPIはCOMをベースにしている[6]。してCOMベースであり、C++を第1級言語としている。2018年時点では、マイクロソフトはCOMのサポートやCOMそのものをやめてしまう計画を持っていない。Explorerのようなネイティブアプリケーションのスクリプト制御のための技術として理想的でもある。COMにおけるあらゆる要素を一意に識別するために開発されたGUIDシステムはマイクロソフトによるUUIDの実装であり、COM以外でもユニークなIDが必要とされる場合に広く利用されている[7]。トランザクションやコンポーネントのキューといったようなCOM+が提供する複数のサービスはエンタープライズな.NETアプリケーションでもまだ重要である。制約はあるものの、.NETはCOMに対して相互運用性のサポートがある。実装することでCOMオブジェクトを利用できる。よって、特定の制約に従った.NETオブジェクトを利用できる。COMと.NETの両方の側からは相手側のオブジェクトがネイティブなオブジェクトに見える。Remotingでは、オブジェクトがプロセスやマシンの境界を越えてリファレンスや値を透過的にマーシャリングできるようにして、COMが持つ数多くのリモート実行の欠点を解決する。割り当てられ、COMコンポーネント同士はクラスIDによって区別される。CLSIDはGUIDで構成されている。各COMコンポーネントは1つ以上のインターフェイスを公開することで機能を提供している。IIDもGUIDで構成されている。COMインターフェイスはプログラミング言語とCOMとを結び付けている。COMコンポーネントへのアクセスは全てインターフェイスを通さなければならない。これによって、プロセスやコンピュータを跨いでCOMコンポーネントにアクセスすることができるようになっている(コンピュータを跨いでのアクセスにはDCOMが必要)。全てのCOMコンポーネントはIUnknownと呼ばれるインターフェイスを継承する必要がある。全てのCOMインターフェイスはIUnknownから派生している。QueryInterfaceという3つのメソッドを持っている。AddRefとReleaseはインターフェイスの生存期間を管理するための参照カウントを実装するメソッドである。QueryInterfaceは、IIDを指定してコンポーネントが実装している他のインターフェイスを取得するメソッドである。これはC++のdynamic_castや、JavaおよびC#の型変換演算子に相当する。備えている必要がある。反射性とは、あるインタフェースから、QueryInterfaceをそのインタフェース自身を表すIIDを与えて呼び出すと、返ってくるインタフェースは元と同じものでなければならないということである。対称性とは、インタフェースAからQueryInterfaceでインタフェースBが取得できる場合、インタフェースBからインタフェースAが取得できなければならないということである。推移性とは、対称性と似ているが、インタフェースBがインタフェースAから取得でき、インタフェースCがインタフェースBから取得できる場合、インタフェースCはインタフェースAから取得できなければならないということである。インタフェースには、インタフェースを実装した関数へのポインタをその宣言時の順に並べた仮想関数テーブルへのポインタが含まれている。1.0のときからOLEシステムとの通信に使われていた。COMはコンポーネント間の通信のためにほかにも多くの標準インタフェースを定めている。データストリームを管理するIStreamが挙げられる。これはファイルストリームのコンポーネントがファイルを読み書きする際に使うことが考えられる。IStreamのReadメソッドとWriteメソッドはストリームに対して読み取りと書き込みを行うことが想定される。他の例として、IOleObjectは、呼び出した側がコンポーネントの境界を決められるメソッドを持っており、また「開く」、「保存」などの操作を行うことができる。コクラスは、COMにおける(オブジェクト指向プログラミングのような)クラスを定義する言語非依存の手段である。1つのコクラスは、1つ以上のインタフェースの具体的な実装を提供する。Basicなどどんな言語でも実装を行うことができる。ProgIDで識別される。クラスIDはGUIDを使った表現である。通常、各コクラスに対しクラスIDを1つ割り当てる。互換性のため、旧バージョンのクラスIDに新バージョンのコクラス実装を登録し、結果的に複数クラスIDが同一コクラスを指し示す場合もある。そのような用途にCoTreatAsClass関数が用意されている。ProgIDは文字列による表現である。InternetExplorer.ApplicationやMsxml2.DOMDocument.6.0など「プログラム名.コンポーネント.バージョン」(バージョンは非必須)という規則である[9]。ProgIDは必須ではなく、コクラスによってはProgIDを持っていない場合もある。ProgIDによる指定でオブジェクトを作成・取得する際には、ProgIDからクラスIDに変換する必要がある。この変換は一意ではなく、特にバージョン指定のないProgIDでは、インストールされているコンポーネントのバージョン次第で、コンピューターごとに異なるCLSIDとなる可能性がある。この処理はプログラミング言語やライブラリによって実装される場合もある。VBScriptなど、オブジェクト作成時にProgIDでの指定のみ可能なプログラミング言語もある。COMは、Windows開発の世界に、実装とインターフェイスを切り離すという概念を意識させることをもたらした。この基本的な概念の延長には、オブジェクト指向におけるポリモーフィズム(多態)がある。1つのインターフェイスに対して複数の実装を用意し、実行時にアプリケーション側が任意の実装を選び、それを区別なく一様に操作することができるということであり、またCOMコンポーネントが要求するインターフェイスを実装するオブジェクトをアプリケーション側で用意して、COMコンポーネントにインターフェイスを通じて操作させることで、コールバック処理などのカスタマイズを実現することもできるということである。して標準化され、プロセス内だけでなくDCOMプロセス間の透過的なコールバック処理をも実現することにつながった。インタフェース定義言語とタイプライブラリ編集COMコンポーネントに関する情報の記述手段として、MIDL(マイクロソフトインタフェース定義言語、IDLも参照)やタイプライブラリがある。MIDLはテキストファイルで主として開発時に用いられる。タイプライブラリは型に関する言語非依存の情報を提供するバイナリファイルであり、開発時だけでなく実行時に参照されることも想定されている。COMコンポーネントの開発では、普通IDLで型を定義することから始める。IDLファイルではオブジェクト指向的なクラスやインタフェース、構造体、列挙体などのユーザ定義型をプログラミング言語に依存せず記述できる。このIDLではC/C++に似たキーワードと、それに追加してインタフェースを定義する「interface」、コクラスを定義する「coclass」、それらの集合を現す「library」という2つのキーワードを使用する。指定したり配列引数とその長さを示す引数との関係を指示したりできる。IDLファイルはMIDLコンパイラで様々なプログラミング言語に向けてコンパイルされる。C/C++用にはインタフェースなどが宣言されたヘッダファイルとGUIDを定義したCのソースファイル、またCOMのメソッド呼び出しをRPC用に変換する「プロキシ」とそれを元に戻す「スタブ」のソースファイルも生成される。MIDLはIDLファイルからタイプライブラリ(.TLBファイル)も作る。BasicやDelphi、.NETのCLRなど)で利用される。その結果タイプライブラリファイルで定義されたコクラスをその言語や環境に持ち込んで使用できるようになる。オブジェクトフレームワークとしてのCOM編集COMの基本原則はそれがオブジェクト指向の哲学に基づいているということである。オブジェクト指向開発と実装を実現するためのプラットフォームである。COMはランタイムフレームワークであるため、型は明示的に識別可能であり実行時に指定可能である必要がある。これを実現するためにGUIDが使われる。それぞれのCOMの型は実行時あるいはコンパイル時に自分の識別用GUIDを指定する。COMの型についての情報がコンパイル時と実行時の両方でアクセスできるようにする必要性から、COMはタイプライブラリを提供する。COMがオブジェクトの相互作用のための動的なフレームワークとしてその能力を発揮するのはタイプライブラリが効果的に利用されているからである。以下の例にあるIDLのコクラス定義を考える。ISomeInterface;};上記のコード断片は、ISomeInterfaceというインターフェイスを実装する、SomeClassという名前のCOMクラスを宣言している。これは概念的には次のようなC++のクラスを定義することに等しい。...};ISomeInterfaceはC++の純粋仮想基底クラスに相当するものである。COMのインターフェイスおよびコクラスを含むIDLファイルはタイプライブラリファイルにコンパイルされる。タイプライブラリはCOMクライアントのコンパイル時あるいは実行時に解釈され、オブジェクトがどのインターフェイスをサポートするかを決定し、オブジェクトのインターフェイスメソッドを呼び出すために利用される。API関数のひとつであるCoCreateInstance()を使用してCOMオブジェクトをインスタンス化することができる。reinterpret_cast<void**>(&pSomeInterface));この例では、ISomeInterfaceインターフェイスを実装するSomeClassオブジェクトへのポインタを取得するためにCOMサブシステムが使われる。これは概念的に次のようなC++のコードと等しい。SomeClass();そしてコクラスはCOMの世界ではオブジェクト指向のクラスである。結果的にプログラミング言語に非依存ということである。レジストリ編集Windowsの場合、COMのクラス、インターフェイス、タイプライブラリはWindowsレジストリにあるGUIDのリストであり、クラスは"HKEY_CLASSES_ROOT\CLSID"に、インターフェイスは"HKEY_CLASSES_ROOT\interface"にある。COMライブラリは各COMオブジェクトが正しいローカルライブラリを特定するためやリモートサービスのネットワーク上の位置を特定するためにレジストリを使用する。DLLサーバー型のCOMコンポーネントはregsvr32(英語版)というコマンドラインプログラムを使用してレジストリ登録および登録解除を行なうが、EXEサーバー型のCOMコンポーネントは自身に/RegServerあるいは/UnRegServerスイッチを付けて起動し、レジストリ登録および登録解除を行なう[10]。システムレジストリを使用する性質上、レジストリ登録されたCOMコンポーネントはコンピュータあるいはネットワーク上のすべてのCOMクライアントから共有される。COMコンポーネントをバージョンアップする際にインターフェイスを変更・追加する場合、旧バージョンをレジストリ登録解除したうえで新バージョンをレジストリ登録し直すか、異なる名前およびGUIDを持つインターフェイスを改めて定義した別のコンポーネントをレジストリ登録する必要がある。前者はバージョンアップの際にCOMクライアントの更新は不要だが、破壊的な仕様変更を避けるなど後方互換性に配慮した設計が求められる。後者は新しいバージョンに対応するCOMクライアントを再作成する必要があるが、複数のバージョンを共存させることができ、バージョン間の互換性を考慮する必要はない。Direct3Dのバージョン7/8/9/10/11/12は、すべて異なるインターフェイスを持つ独立したCOMコンポーネント[11]であり、同一コンピュータ上に共存できる。典型的にいって、COMにおける最良のアプローチは、機能を拡張するためには新しいインターフェイスを定義することである[12]。COMコンポーネントのマイナーバージョンアップの際は、通例既存のインターフェイスを継承して新たなインターフェイスを定義する手法が採られる。10.0あるいは11.0のインターフェイスからそれぞれ派生した新しいインターフェイスを定義する方法で機能拡張が行なわれている。XP以降では、「分離アプリケーションとSide-by-Sideアセンブリ」と呼ばれる仕組みを使い、レジストリではなくマニフェストファイルを使用してコンポーネント依存関係を解決することも可能である。この仕組みを用いることで、COMコンポーネントをシステム全体で共有せず、アプリケーションごとにプライベートアセンブリとして配布・運用することも可能となる。基本的なCOMのインタフェースであるIUnknown(全てのCOMインタフェースはここから派生する)は、QueryInterface()による機能の確認と、AddRef()およびRelease()を通じたオブジェクトの寿命の管理という2つの主要な概念をサポートする[13]。参照カウントと機能の確認は(オブジェクトの各インタフェースに対してではなく)オブジェクトに対して適用される。従って注意深く実装する必要がある。インタフェースへのアクセスを要求したクライアントが存在している限り個々のオブジェクトが生存していることを保障し、逆にオブジェクトを使用していたすべてのコードが終了してそのオブジェクトが不要になった時にオブジェクトを適切に処分するため、インタフェースの参照カウントというテクニックがCOMでは要求される。COMオブジェクトは参照カウントが0に達したときに自分のメモリを自分で解放する責任がある。これを実装するため、COMオブジェクトは一般的に参照カウントのための整数値を持つ。オブジェクトのインタフェースからAddRef()が呼ばれるとこの整数値が加算される。Release()が呼ばれるとこの整数値は減算される。AddRef()とRelease()はCOMオブジェクトのクライアントがそのオブジェクトの寿命に関与できる唯一の手段である。内部の整数値はCOMオブジェクトのプライベートなメンバーであり、直接的にはアクセスできない。AddRef()の目的は、COMオブジェクトへの新しい参照が生じて、その参照が正当である限り生存し続ける必要があるということを、そのCOMオブジェクトに対して示すことである。Release()の目的は、クライアント(またはクライアントコードの一部)がもうオブジェクトを必要としなくなり、もし参照カウントが0に達した場合にはオブジェクトが自らを破棄するであろうということを示すことである。Basic)では自動参照カウントが提供されるため、COMオブジェクトの開発者はソースコード中で内部参照カウントを明示的に保持する必要がない。C言語でCOMを利用する場合、明示的な参照カウントの操作が必要である。C++では、自分自身でそれを管理することもできるし、参照カウントを全部管理してくれるスマートポインタ(ATL::CComPtrなど)を利用することも選択できる。下記はCOMオブジェクトで適切な参照カウントの制御を簡単にするためのAddRef()とRelease()を呼び出す際の一般的なガイドラインである。(戻り値またはoutパラメーターで)インタフェースの参照を返す関数(オブジェクトメソッドとグローバル関数のいずれも)は、それを返却する前に、背後にあるオブジェクトの参照カウントを加算しておくべきである。従って関数やメソッドの内部で、AddRef()が(返却する)インタフェースの参照に対して呼び出される。IUnknownインタフェースのQueryInterface()メソッドはこの実例である。従って、リターンされたインタフェースの参照は既に加算されており、リターンされたインタフェースの参照のAddRefを再度呼びだす必要がないということを開発者は理解していなければならない。インタフェースのポインタが上書きされるかスコープから外れる前にインタフェースの参照からRelease()を呼び出さなければならない。インタフェースの参照ポインタからコピーを作る場合、そのポインタでAddRef()を呼び出すべきである。結局この場合は、背後にあるオブジェクトのもう1つの参照を実際に作成している。インタフェースを参照するだけで内部リソースを割り当てる必要があることからインタフェース毎に参照をカウントするようにオブジェクトが実装されているかもしれないため、参照した特定のインタフェースに対してAddRef()とRelease()を呼び出さなければならない。これらの関数の追加の呼び出しはケーブルを超えてリモートオブジェクトに送信されない。プロキシはリモートオブジェクトの参照を1つだけ保持し、ローカルの参照カウントを管理する。ATLは高レベルのCOM開発パラダイムを提供する。ATLはまた、スマートポインタオブジェクトを提供することによってCOMクライアントのアプリケーション開発者が参照カウントを直接管理しなくてもよいようにする。(JavaScript)、Delphiなどのライブラリや言語がCOMに対応している。インストール編集COMはクラスファクトリを利用してCOMオブジェクトのインストール(つまり生成)プロセスを標準化する。COMオブジェクトを作成するため、2つの関連した項目が存在していなければならない。関連付けられていなければならない。クラスファクトリとも関連付けられていなければならない(レジストリを利用して行う)。クラスファクトリ自身はCOMオブジェクトである。これはIClassFactoryまたはIClassFactory2インタフェースを持つオブジェクトでなければならない(後者はライセンス管理をサポートしているインタフェースである)。これらのオブジェクトは他のオブジェクトを生成する責任がある。クラスファクトリオブジェクトは一般的にはCOMオブジェクト自身と同じ実行ファイル内(つまりサーバーコード内)に含まれている。ターゲットオブジェクトを作成するようにクラスファクトリを呼び出すとき、このターゲットオブジェクトのクラスIDが提供されていなければならない。このようにしてクラスファクトリはどのクラスのオブジェクトをインスタンス化するのかを把握する。単一のクラスファクトリオブジェクトは複数のクラスのオブジェクトを生成するかもしれない。異なるクラスIDを持つ2つのオブジェクトが同じクラスファクトリオブジェクトによって生成されるかもしれない。これはCOMシステムにとっては曖昧なものではない。別のオブジェクトにオブジェクト生成の責任を委ねることにより、抽象度が非常に高くなり、開発者に高い柔軟性をもたらす。シングルトンやその他のオブジェクト生成パターンの実装が容易になる。ファクトリオブジェクトはCOMオブジェクトのメモリ割り当てからアプリケーションの呼び出しを守る。クライアントアプリケーションがクラスファクトリオブジェクトを入手できるようにする必要性から、COMサーバーはそれらを適切に公開しなければならない。クラスファクトリはサーバーコードの特質上、別の方法で公開される。サーバーはDllGetClassObject()というグローバル関数をエクスポートしなければならない。API関数でクラスファクトリを登録しなければならない。下記はクラスファクトリを利用したオブジェクト生成のシーケンスの一般的な概略である。API関数CoGetClassObject()で取得する。CoGetClassObject()を呼び出すためには作成するオブジェクトのクラスIDが提供されていなければならない。C++によるコード例を以下に示す。(LPVOID*)&pIClassFactory);上記のコードはCLSID_SomeObjectというクラスIDによって識別されたCOMオブジェクトのクラスファクトリが必要であることを示している。このクラスファクトリオブジェクトはIClassFactoryインタフェースで返される。返却されたクラスファクトリオブジェクトを使って元々意図していたCOMオブジェクトのインタフェースを生成するように要求する。C++によるコード例を以下に示す。NULL;}上記のコードは、クラスファクトリオブジェクトのCreateInstance()メソッドを使用して、IID_ISomeObjectというGUIDで識別されるインタフェースを公開しているオブジェクトを生成することを示している。このオブジェクトのISomeObjectインタフェースへのポインタが返される。クラスファクトリオブジェクトはそれ自身がCOMオブジェクトであることから、もう必要なければリリースする必要があるということにも注意してほしい(要するにこれのRelease()メソッドを呼び出さなければならない)。上記はオブジェクトをインスタンス化するクラスファクトリの非常に基本的な使用例である。APIを直接利用しないものもある。APIを内部で呼び出しており、そしてCOMオブジェクトを生成するためにクラスファクトリのCreateInstance()メソッドを使用している。CreateObject()というオブジェクトをインスタンス化するためのグローバル関数の他に、C++ではnewを利用できる。APIで)目的のオブジェクトのクラスファクトリオブジェクトを取得することを隠蔽する。PowerBuilderのPowerScriptのように上位レベルのオブジェクトを生成するコンストラクタを提供する言語もある。CoGetClassObject()とIClassFactoryインタフェースを使った非常に基本的なオブジェクト生成手法もまだ利用できる。リフレクション編集COMの初期の時代、オブジェクトがどのような機能を提供するのかということをクライアントから確認するためには、インスタンスを実際に生成して(IUnknownインタフェースの)QueryInterfaceメソッドを呼び出してみるしかなかった。この検証方法は、特定の業務のために適切なコンポーネントを選択したり、オブジェクトが提供するメソッドの使用方法を開発者が理解できるようにしたりといったところで、多くのアプリケーションにとって不便であるということになった。結果的にコンポーネントを完全に確認できるCOMタイプライブラリが導入された。タイプライブラリは、コンポーネントのCLSID、コンポーネント実装のインタフェースのIID、これらのインタフェースの各メソッドの解説といった情報を含んでいる。StudioのようなRAD環境でクライアントアプリケーションの開発者を支援するために利用されている。バイナリ標準であり、タイプライブラリすなわちバイナリで定義されたデータ型とインターフェイスを解釈する機能を実装できさえすれば、いかなるプログラミング言語でも開発できる。ランタイムライブラリ(厳密に言えばプログラマ)は、COMの環境に立ち入って、インスタンス化してCOMオブジェクトの参照をカウントし、バージョン情報からオブジェクトを問い合わせて、新しいバージョンのオブジェクトを利用してコーディングし、新しいバージョンが利用可能でない場合は古いバージョンでも動作するようにフォールトレトラントをコーディングするといった責任がある。アプリケーションとネットワークの透過性編集プロセス内から、またはコンピューター内のプロセスの境界を越えて、あるいはDCOMテクノロジを利用してネットワークを超えて、COMオブジェクトをインスタンス化して参照できる。プロセスの外やリモートにあるオブジェクトはメソッドコールや戻り値をやりとりするためにマーシャリングを利用できる。マーシャリングでは、オブジェクトや、オブジェクトを利用しているコードは見えない。COMのスレッド編集COMでは、アパートメントモデルとして知られているコンセプトによってスレッドの問題を解決している。ここで言うアパートとは、単一のスレッドまたはスレッドのグループの中にある実行コンテキストが1つまたは複数のCOMオブジェクトに関連づけられていることを指している。アパートメントでは以下のガイドラインが関連するスレッドとオブジェクトのために示される。1つのCOMオブジェクトは1つのアパートメントだけに関連づけられる。オブジェクトが実行時に生成された時点で関連づけられる。オブジェクトの初期化後は一生そのアパートメントに属する。COMスレッド(つまりCOMオブジェクトを生成したか、COMのメソッドコールが行われたスレッド)もまた1つのアパートメントに関連づけられる。COMオブジェクトと同様、スレッドとアパートメントの関連づけは初期化時に決定される。各COMのスレッドもまた終了するまで指定されたアパートメントに属し続ける。メソッドを呼び出すスレッドとオブジェクトが同じアパートメントに属す場合、COMの介入無しに直接呼び出される。メソッドを呼び出すスレッドとオブジェクトが異なるアパートメントに属す場合、そのメソッド呼び出しはマーシャリングを利用して行われる。これにはプロキシとスタブが利用される。3つのアパートメントモデルがある。各アパートメントは、オブジェクトの内部状態が複数のスレッドを超えて同期されるかどうかという1つのメカニズムを表している。シングルスレッドアパートメントモデルは非常に一般的に利用されているモデルである。ここではCOMオブジェクトはデスクトップアプリケーションのユーザーインタフェースに似た立場にある。STAモデルでは、単一のスレッドがオブジェクトのメソッドを動かすことに専念している。常に単一のスレッドでオブジェクトのメソッドが実行される。このようなアパートメントでは、アパートメントの外にあるスレッドからのメソッドコールはマーシャリングされ、(標準のWindowsのメッセージキューを利用して)システムによって自動的にキューに入れられる。これによりその呼び出しが完了してから各オブジェクトのメソッド呼び出しが実行されるようになり、レースコンディションや同期性の欠如といった心配がない。プロセスの中で最初に作られたSTAは特にメインSTAと呼ばれ、マルチスレッドを全く考慮していないCOMオブジェクトはメインSTAだけで動作させられる。COMオブジェクトのメソッドの同期を自分で取りたい場合、メソッドを呼び出したスレッドと同一のスレッドでメソッドを処理するようにできる。これをマルチプルスレッドアパートメントと呼ぶ。STAスレッドからのMTAオブジェクトのメソッド呼び出しはマーシャリングされる。プロセスは複数のCOMオブジェクトで構成でき、その一部をSTAにしてそれ以外はMTAを利用するというようにできる。COM+で導入されたスレッド中立アパートメントは、オブジェクトのメソッド呼び出しを管理する必要がない場合に用いられる。唯一の条件はオブジェクトの全てのメソッドがリエントラント(再入可能)でなければならないということである。中立アパートメントに属すオブジェクトのメソッドは、STAスレッド・MTAスレッド、どちらからでもマーシャリングなしに直接呼び出せる。グローバル株式会社訳、アスキー出版局、1997年。4-756-12176-4。DirectXのCOMは主にC++から使われることを想定した独自実装となっており、標準的なCOMの流儀に則っていない部分もある。オブジェクトの生成にCoCreateInstance()関数を利用せずD3D11CreateDevice()のような独自のファクトリ関数を用意している、IXAudio2SourceVoiceのようにIUnknown派生でないインターフェイスが存在している、といった具合である。Studioのプロジェクトファイルおよびソリューションファイルでは、各プロジェクトを識別するためにGUIDが使われる。2016年6月12日閲覧。3.0のもとで利用可能です。プライバシーデスクトップ。