singleton question

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • ben chang

    #1

    singleton question

    i'm hacking at some code originally written for VC++, trying to port to
    linux GCC 4. the linker returns multiple-definition errors with a
    singleton object, which i guess is not a problem in visual c++. i'll try
    to excerpt the relevant parts without posting all the source files (it's
    the maya exporter for the Ogre 3D engine).

    there's a pretty standard-looking Singleton template, and in a file called
    "materialSe t.h" we have a class using it:

    /////
    namespace OgreMayaExporte r
    {
    class MaterialSet : public Singleton<Mater ialSet>
    {
    (nothing unusual in here, so i won't bore you... )
    };

    template<Materi alSet Singleton<Mater ialSet>::ms_Sin gleton=0;
    }

    /////

    now, materialSet.h is included directly or indirectly by a bunch of source
    files (blendshape.cpp , ogreExporter.cp p, skeleton.cpp, mesh.cpp). so i get
    this linker error:

    g++ -c -I. -I../include -I/usr/autodesk/maya/include -I/usr/X11R6/include -I/usr/local/include/OGRE -pipe -D_BOOL -DLINUX -DI386 -ffast-math submesh.cpp
    g++ -shared -o OgreExport blendshape.o material.o mesh.o ogreExporter.o paramlist.o particles.o skeleton.o submesh.o -L/usr/autodesk/maya/lib -lOpenMaya -lOgreMain
    mesh.o:(.bss+0x 0): multiple definition of `OgreMayaExport er::Singleton<O greMayaExporter ::MaterialSet>: :ms_Singleton'
    blendshape.o:(. bss+0x0): first defined here
    ogreExporter.o: (.bss+0x0): multiple definition of `OgreMayaExport er::Singleton<O greMayaExporter ::MaterialSet>: :ms_Singleton'
    blendshape.o:(. bss+0x0): first defined here
    skeleton.o:(.bs s+0x0): multiple definition of `OgreMayaExport er::Singleton<O greMayaExporter ::MaterialSet>: :ms_Singleton'
    blendshape.o:(. bss+0x0): first defined here
    submesh.o:(.bss +0x0): multiple definition of `OgreMayaExport er::Singleton<O greMayaExporter ::MaterialSet>: :ms_Singleton'
    blendshape.o:(. bss+0x0): first defined here

    this declaration is complicated enough that it's a bit hard to wrap my
    head around, but isn't this essentially repeatedly declaring a global
    (within the namespace) variable, which is what Singletons are supposed to
    avoid? is this a difference between gcc and msvc?

    thanks,

    -ben
  • Rolf Magnus

    #2
    Re: singleton question

    ben chang wrote:
    i'm hacking at some code originally written for VC++, trying to port to
    linux GCC 4. the linker returns multiple-definition errors with a
    singleton object, which i guess is not a problem in visual c++. i'll try
    to excerpt the relevant parts without posting all the source files (it's
    the maya exporter for the Ogre 3D engine).
    >
    there's a pretty standard-looking Singleton template, and in a file called
    "materialSe t.h" we have a class using it:
    >
    /////
    namespace OgreMayaExporte r
    {
    class MaterialSet : public Singleton<Mater ialSet>
    {
    (nothing unusual in here, so i won't bore you... )
    };
    >
    template<Materi alSet Singleton<Mater ialSet>::ms_Sin gleton=0;
    The above line defines Singleton<Mater ialSet>::ms_Sin gleton. If this is in a
    header and that header is included in multiple files, you'll get multiple
    definitions of that object.
    this declaration is complicated enough that it's a bit hard to wrap my
    head around, but isn't this essentially repeatedly declaring a global
    (within the namespace) variable, which is what Singletons are supposed to
    avoid?
    It's repeatedly _defining_ the very same namespace-level variable, which any
    program is supposed to avoid. Put the definition into an implementation
    file, not a header.


    Comment

    • James Kanze

      #3
      Re: singleton question

      On Jul 16, 6:40 am, ben chang <devn...@NOSPAM .bcchang.comwro te:
      i'm hacking at some code originally written for VC++, trying to port to
      linux GCC 4. the linker returns multiple-definition errors with a
      singleton object, which i guess is not a problem in visual c++. i'll try
      to excerpt the relevant parts without posting all the source files (it's
      the maya exporter for the Ogre 3D engine).
      there's a pretty standard-looking Singleton template, and in a file called
      "materialSe t.h" we have a class using it:
      /////
      namespace OgreMayaExporte r
      {
      class MaterialSet : public Singleton<Mater ialSet>
      {
      (nothing unusual in here, so i won't bore you... )
      };
      template<Materi alSet Singleton<Mater ialSet>::ms_Sin gleton=0;
      What is this line supposed to be doing? If the template
      Singleton is written correctly, it shouldn't be necessary. As
      it is, you're defining an explicit specialization of a template
      data member (presumably static). Explicit specializations
      aren't templates, however, they're instantations of templates,
      and thus normal classes, functions or data. You wouldn't expect
      defining normal data like this in a header file to work, and
      that's really what you're doing. (The result is a multiple
      definition, a violation of the one definition rule, and thus
      undefined behavior. Most compilers will complain in the link
      phase, but no diagnostic is actually required.)

      I'm not sure why you're declaring the instance anyway.
      Normally, depending on the variant of singleton you're using,
      the instance is either a local variable of the
      Singleton::inst ance function, or allocated dynamically. In the
      latter case, the Singleton template might declare a pointer as a
      static, in which case, the header which defines the template
      would require something like:

      template< typename T >
      T* Singleton< T >::ourInstanc e = 0 ;

      Note that unlike your definition, this is also a template (and
      not an explicit instantiation), and so should behave like all
      templates, with multiple definitions being allowed (as long as
      they are the same), and the compiler ensuring that everything
      works as if there were a single definition for each
      instantiation.
      }
      --
      James Kanze (GABI Software) email:james.kan ze@gmail.com
      Conseils en informatique orientée objet/
      Beratung in objektorientier ter Datenverarbeitu ng
      9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34

      Comment

      Working...