0

nm でリストされている単一のメソッドに対して複数のエントリがあるのは正常ですか? 私は以下を実行しました:

nm -C myObjectFile.o | grep MyObject::

そして以下を受け取りました。

... stuff...
... stuff...
0000027e0 T MyObject::MyObject(MyDepend*)
0000027e0 T MyObject::MyObject(MyDepend*)
000000030 T MyObject::~MyObject()
000000000 T MyObject::~MyObject()
000000000 T MyObject::~MyObject()
000000060 T non-virtual thunk to MyObject::~MyObject()
000000020 T non-virtual thunk to MyObject::~MyObject()

これは私には間違っているようです。それはあなたには間違っているように見えますか?もしそうなら、なぜそれが間違っているのか、何が原因なのかを詳しく説明していただけますか? 特定の状況下でのみ正しい場合は、nm 出力を見ている問題について詳しく説明し、そこから進むことができます。

4

1 に答える 1

1

場合によっては、デマングラーは異なる入力を同じ出力にデマングルします。これは時々やや混乱するかもしれませんが、そうでない場合はそれほど混乱しないので、私はそう思います。たとえば、デマングラーは gdb によって使用され、このアプローチにより、コンストラクターのブレークポイントは、ユーザーによる追加の労力なしで正しいことを実行できます。たぶん、いくつかの考えと作業で、ここでいくつかの改善が可能です。

とにかく、ここに簡単な例があります:

class K
{
  K ();
  virtual ~K();
};

K::K() { }
K::~K() { }

でコンパイルし-gてから実行すると、次のnm -Cような結果が表示されます。

$ nm -C q.o
         U operator delete(void*)
0000000000000000 T K::K()
0000000000000000 T K::K()
0000000000000048 T K::~K()
0000000000000018 T K::~K()
0000000000000018 T K::~K()
0000000000000000 V typeinfo for K
0000000000000000 V typeinfo name for K
0000000000000000 V vtable for K
         U vtable for __cxxabiv1::__class_type_info

しかし、plain を実行するとどうなるか見てみましょうnm:

$ nm q.o
         U _ZdlPv
0000000000000000 T _ZN1KC1Ev
0000000000000000 T _ZN1KC2Ev
0000000000000048 T _ZN1KD0Ev
0000000000000018 T _ZN1KD1Ev
0000000000000018 T _ZN1KD2Ev
0000000000000000 V _ZTI1K
0000000000000000 V _ZTS1K
0000000000000000 V _ZTV1K
         U _ZTVN10__cxxabiv117__class_type_infoE

ここでは、基になるシンボルが異なることがより明確にわかります。

ここから、GCC が従う C++ ABIに進むことができます。特にコンストラクタとデストラクタのマングリングに関するセクションに。歴史的な理由から、これは「Itanium」ABI と呼ばれていますが、実際にはすべてのプラットフォームで (おそらくマイナーなバリアントと共に) 使用されています。

このセクションでは名前の意味を説明しますが、完全に理解するにはドキュメントをさらに深く掘り下げる必要があります。基本的な考え方は、C++ の実装では、コンストラクターとデストラクターへの異なるエントリ ポイントが必要であるということです。これは、異なるエントリ ポイントに異なるシンボルを提供することによって行われます。

于 2015-06-29T13:19:27.903 に答える