linking error for static member variables

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

    linking error for static member variables

    Hi everyone,

    I have a linking error when using gcc4.2 and static member variables.
    The class template definition is something around the following:

    template<>
    class Element<L2_t: public Element_common< L2, Side<2,2 {

    public:

    static const ubyte_t dim_ = 2;
    static const ubyte_t num_nodes_ = 2;
    static const ubyte_t gauss_pts_= 3;

    // member functions
    };

    Undefined symbols:
    "fea::Element<( fea::Element_ty pe)1>::gauss_pt s_", referenced from:
    __ZN3fea7Elemen tILNS_12Element _typeE1EE10gaus s_pts_E
    $non_lazy_ptr in element.o
    "fea::Element<( fea::Element_ty pe)2>::gauss_pt s_", referenced from:
    __ZN3fea7Elemen tILNS_12Element _typeE2EE10gaus s_pts_E
    $non_lazy_ptr in element.o
    "fea::Element<( fea::Element_ty pe)3>::gauss_pt s_", referenced from:
    __ZN3fea7Elemen tILNS_12Element _typeE3EE10gaus s_pts_E
    $non_lazy_ptr in element.o
    ld: symbol(s) not found

    The strange thing is that I have many other static variables with the
    same kind of definition (same type and const as you can see) but it
    only complaints about the gauss_pts_ member variable. I solved the
    problem by moving the definition to the cpp file as follows:

    // in cpp file
    const ubyte_t Element<L2_t>:: gauss_pts_ = 3;

    But I want to understand really what is happening here. When I compile
    the code with gcc4.3, the problem disappears. So, is this a bug in the
    compiler?

    Thanks for the help,

    aa
  • Victor Bazarov

    #2
    Re: linking error for static member variables

    aaragon wrote:
    I have a linking error when using gcc4.2 and static member variables.
    The class template definition is something around the following:
    >
    template<>
    class Element<L2_t: public Element_common< L2, Side<2,2 {
    >
    public:
    >
    static const ubyte_t dim_ = 2;
    static const ubyte_t num_nodes_ = 2;
    static const ubyte_t gauss_pts_= 3;
    WTH is 'ubyte_t'?
    >
    // member functions
    };
    >
    Undefined symbols:
    "fea::Element<( fea::Element_ty pe)1>::gauss_pt s_", referenced from:
    __ZN3fea7Elemen tILNS_12Element _typeE1EE10gaus s_pts_E
    $non_lazy_ptr in element.o
    "fea::Element<( fea::Element_ty pe)2>::gauss_pt s_", referenced from:
    __ZN3fea7Elemen tILNS_12Element _typeE2EE10gaus s_pts_E
    $non_lazy_ptr in element.o
    "fea::Element<( fea::Element_ty pe)3>::gauss_pt s_", referenced from:
    __ZN3fea7Elemen tILNS_12Element _typeE3EE10gaus s_pts_E
    $non_lazy_ptr in element.o
    ld: symbol(s) not found
    >
    The strange thing is that I have many other static variables with the
    same kind of definition (same type and const as you can see) but it
    only complaints about the gauss_pts_ member variable. I solved the
    problem by moving the definition to the cpp file as follows:
    >
    // in cpp file
    const ubyte_t Element<L2_t>:: gauss_pts_ = 3;
    >
    But I want to understand really what is happening here.
    Not much. Any static member variable/constant has to be defined if used
    outside of the class. Since you didn't show us how those constants are
    used, the assumption is that they *are* used outside and *must* be
    defined or you're in violation of the ODR.
    When I compile
    the code with gcc4.3, the problem disappears. So, is this a bug in the
    compiler?
    Not from where I sit.

    V
    --
    Please remove capital 'A's when replying by e-mail
    I do not respond to top-posted replies, please don't ask

    Comment

    • aaragon

      #3
      Re: linking error for static member variables

      On Oct 20, 7:45 am, Victor Bazarov <v.Abaza...@com Acast.netwrote:
      aaragon wrote:
      I have a linking error when using gcc4.2 and static member variables.
      The class template definition is something around the following:
      >
         template<>
         class Element<L2_t: public Element_common< L2, Side<2,2 {
      >
         public:
      >
                 static const ubyte_t dim_ = 2;
                 static const ubyte_t num_nodes_ = 2;
                 static const ubyte_t gauss_pts_= 3;
      >
      WTH is 'ubyte_t'?
      >
      >
      >
      just a type definition to cope with the way I name things.
      >
      >
              // member functions
              };
      >
      Undefined symbols:
        "fea::Element<( fea::Element_ty pe)1>::gauss_pt s_", referenced from:
            __ZN3fea7Elemen tILNS_12Element _typeE1EE10gaus s_pts_E
      $non_lazy_ptr in element.o
        "fea::Element<( fea::Element_ty pe)2>::gauss_pt s_", referenced from:
            __ZN3fea7Elemen tILNS_12Element _typeE2EE10gaus s_pts_E
      $non_lazy_ptr in element.o
        "fea::Element<( fea::Element_ty pe)3>::gauss_pt s_", referenced from:
            __ZN3fea7Elemen tILNS_12Element _typeE3EE10gaus s_pts_E
      $non_lazy_ptr in element.o
      ld: symbol(s) not found
      >
      The strange thing is that I have many other static variables with the
      same kind of definition (same type and const as you can see) but it
      only complaints about the gauss_pts_ member variable. I solved the
      problem by moving the definition to the cpp file as follows:
      >
              // in cpp file
         const ubyte_t Element<L2_t>:: gauss_pts_ = 3;
      >
      But I want to understand really what is happening here.
      >
      Not much.  Any static member variable/constant has to be defined if used
      outside of the class.  Since you didn't show us how those constants are
      used, the assumption is that they *are* used outside and *must* be
      defined or you're in violation of the ODR.
      >

      It is defined, when inside a class you do something like

      static const int test = 2;

      you're defining inline the value of the constant. That is exacly what
      I was doing before, but the linker couldn't find it. Weird thing is
      that only happened with one varible, the other static constants were
      defined in the same way, but they didn't give me problems. So there
      must be a problem with the copmiler.

       When I compile
      >
      the code with gcc4.3, the problem disappears. So, is this a bug in the
      compiler?
      >
      Not from where I sit.
      >
      V
      --
      Please remove capital 'A's when replying by e-mail
      I do not respond to top-posted replies, please don't ask

      Comment

      • Victor Bazarov

        #4
        Re: linking error for static member variables

        aaragon wrote:
        On Oct 20, 7:45 am, Victor Bazarov <v.Abaza...@com Acast.netwrote:
        >aaragon wrote:
        >>I have a linking error when using gcc4.2 and static member variables.
        >>The class template definition is something around the following:
        >> template<>
        >> class Element<L2_t: public Element_common< L2, Side<2,2 {
        >> public:
        >> static const ubyte_t dim_ = 2;
        >> static const ubyte_t num_nodes_ = 2;
        >> static const ubyte_t gauss_pts_= 3;
        >WTH is 'ubyte_t'?
        >>
        >>
        >>
        >
        just a type definition to cope with the way I name things.
        Well, the language prohibits initialisations of static const data
        members *unless* they are of an *integral type*. If your 'ubyte_t' is
        not integral, your code is ill-formed.
        >> // member functions
        >> };
        >>Undefined symbols:
        >> "fea::Element<( fea::Element_ty pe)1>::gauss_pt s_", referenced from:
        >> __ZN3fea7Elemen tILNS_12Element _typeE1EE10gaus s_pts_E
        >>$non_lazy_p tr in element.o
        >> "fea::Element<( fea::Element_ty pe)2>::gauss_pt s_", referenced from:
        >> __ZN3fea7Elemen tILNS_12Element _typeE2EE10gaus s_pts_E
        >>$non_lazy_p tr in element.o
        >> "fea::Element<( fea::Element_ty pe)3>::gauss_pt s_", referenced from:
        >> __ZN3fea7Elemen tILNS_12Element _typeE3EE10gaus s_pts_E
        >>$non_lazy_p tr in element.o
        >>ld: symbol(s) not found
        >>The strange thing is that I have many other static variables with the
        >>same kind of definition (same type and const as you can see) but it
        >>only complaints about the gauss_pts_ member variable. I solved the
        >>problem by moving the definition to the cpp file as follows:
        >> // in cpp file
        >> const ubyte_t Element<L2_t>:: gauss_pts_ = 3;
        >>But I want to understand really what is happening here.
        >Not much. Any static member variable/constant has to be defined if used
        >outside of the class. Since you didn't show us how those constants are
        >used, the assumption is that they *are* used outside and *must* be
        >defined or you're in violation of the ODR.
        >>
        >
        >
        It is defined, when inside a class you do something like
        >
        static const int test = 2;
        >
        you're defining inline the value of the constant.
        Nope. It's declared and initialised. It's not defined. It's only
        defined when you can say that the memory for it is allocated and *where*
        it is allocated. Unless you do

        const int <classname>::te st;

        in the *namespace* scope somewhere in a translation unit, the data
        member is *undefined*.
        That is exacly what
        I was doing before, but the linker couldn't find it. Weird thing is
        that only happened with one varible, the other static constants were
        defined in the same way, but they didn't give me problems. So there
        must be a problem with the copmiler.
        Sure. What else could it be?.. Stupid compilers!

        V
        --
        Please remove capital 'A's when replying by e-mail
        I do not respond to top-posted replies, please don't ask

        Comment

        • aaragon

          #5
          Re: linking error for static member variables

          On Oct 20, 2:38 pm, Victor Bazarov <v.Abaza...@com Acast.netwrote:
          aaragon wrote:
          On Oct 20, 7:45 am, Victor Bazarov <v.Abaza...@com Acast.netwrote:
          aaragon wrote:
          >I have a linking error when using gcc4.2 and static member variables.
          >The class template definition is something around the following:
          >   template<>
          >   class Element<L2_t: public Element_common< L2, Side<2,2 {
          >   public:
          >           static const ubyte_t dim_ = 2;
          >           static const ubyte_t num_nodes_ = 2;
          >           static const ubyte_t gauss_pts_= 3;
          WTH is 'ubyte_t'?
          >
          just a type definition to cope with the way I name things.
          >
          Well, the language prohibits initialisations of static const data
          members *unless* they are of an *integral type*.  If your 'ubyte_t' is
          not integral, your code is ill-formed.
          >
          u_byte is just a type definition for an unsigned short, which is of an
          integral type. The rest of the static constant member variables were
          also of the same type but only this one game the problem. Weird.
          >
          >
          >        // member functions
          >        };
          >Undefined symbols:
          >  "fea::Element<( fea::Element_ty pe)1>::gauss_pt s_", referenced from:
          >      __ZN3fea7Elemen tILNS_12Element _typeE1EE10gaus s_pts_E
          >$non_lazy_pt r in element.o
          >  "fea::Element<( fea::Element_ty pe)2>::gauss_pt s_", referenced from:
          >      __ZN3fea7Elemen tILNS_12Element _typeE2EE10gaus s_pts_E
          >$non_lazy_pt r in element.o
          >  "fea::Element<( fea::Element_ty pe)3>::gauss_pt s_", referenced from:
          >      __ZN3fea7Elemen tILNS_12Element _typeE3EE10gaus s_pts_E
          >$non_lazy_pt r in element.o
          >ld: symbol(s) not found
          >The strange thing is that I have many other static variables with the
          >same kind of definition (same type and const as you can see) but it
          >only complaints about the gauss_pts_ member variable. I solved the
          >problem by moving the definition to the cpp file as follows:
          >        // in cpp file
          >   const ubyte_t Element<L2_t>:: gauss_pts_ = 3;
          >But I want to understand really what is happening here.
          Not much.  Any static member variable/constant has to be defined if used
          outside of the class.  Since you didn't show us how those constants are
          used, the assumption is that they *are* used outside and *must* be
          defined or you're in violation of the ODR.
          >
          It is defined, when inside a class you do something like
          >
             static const int test = 2;
          >
          you're defining inline the value of the constant.
          >
          Nope.  It's declared and initialised.  It's not defined.  It's only
          defined when you can say that the memory for it is allocated and *where*
          it is allocated.  Unless you do
          >
             const int <classname>::te st;
          >
          in the *namespace* scope somewhere in a translation unit, the data
          member is *undefined*.
          >
           That is exacly what
          >
          I was doing before, but the linker couldn't find it. Weird thing is
          that only happened with one varible, the other static constants were
          defined in the same way, but they didn't give me problems. So there
          must be a problem with the copmiler.
          >
          Sure.  What else could it be?..  Stupid compilers!
          Indeed, stupid compilers!
          >
          V
          --
          Please remove capital 'A's when replying by e-mail
          I do not respond to top-posted replies, please don't ask
          Thanks for answering my post.

          aa

          Comment

          Working...