Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. General Programming
  3. C / C++ / MFC
  4. class is missing "type" - why ?

class is missing "type" - why ?

Scheduled Pinned Locked Moved C / C++ / MFC
helphardwarevisual-studioquestion
3 Posts 3 Posters 0 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • V Offline
    V Offline
    Vaclav_
    wrote on last edited by
    #1

    Never mind, instead of trying to find the bug in my code I am going to rebuild the classes, they need clean-up anyway. I have , so far , two relatively similar classes dealing with embedded processor hardware. Here is a code snippet, .... class IDE_USBD; class IDE_HCD; class IDE_ILI9341 { public: class IDE_HCD hcd; class IDE_USBD usbd(); .... If I do not include parenthesizes in implementation of class IDE_USBD I get this error IDE_ILI9341.h:371: error: field 'usbd' has incomplete type class IDE_USBD usbd; ^ exit status 1 field 'usbd' has incomplete type If I add them to class IDE_HCD hcd(); than I get this error: gpf_isr = hcd.UOTGHS_Handler; ^ IDE_ILI9341.h:2351: error: '((IDE_ILI9341*)this)->IDE_ILI9341::hcd' does not have class type hcd.HCD_Init(); ^ exit status 1 '((IDE_ILI9341*)this)->IDE_ILI9341::hcd' does not have class type Both classes have #include files before the IDE_ILI9341 gets implemented , I checked that. Now adding or removing parentheses makes it work, it ain't broke , but why are the parenthesizes needed for IDE_USBD? BTW that class has only default constructor implemented at this time. Help solving this puzzle will be appreciated. Cheers Vaclav

    L G 2 Replies Last reply
    0
    • V Vaclav_

      Never mind, instead of trying to find the bug in my code I am going to rebuild the classes, they need clean-up anyway. I have , so far , two relatively similar classes dealing with embedded processor hardware. Here is a code snippet, .... class IDE_USBD; class IDE_HCD; class IDE_ILI9341 { public: class IDE_HCD hcd; class IDE_USBD usbd(); .... If I do not include parenthesizes in implementation of class IDE_USBD I get this error IDE_ILI9341.h:371: error: field 'usbd' has incomplete type class IDE_USBD usbd; ^ exit status 1 field 'usbd' has incomplete type If I add them to class IDE_HCD hcd(); than I get this error: gpf_isr = hcd.UOTGHS_Handler; ^ IDE_ILI9341.h:2351: error: '((IDE_ILI9341*)this)->IDE_ILI9341::hcd' does not have class type hcd.HCD_Init(); ^ exit status 1 '((IDE_ILI9341*)this)->IDE_ILI9341::hcd' does not have class type Both classes have #include files before the IDE_ILI9341 gets implemented , I checked that. Now adding or removing parentheses makes it work, it ain't broke , but why are the parenthesizes needed for IDE_USBD? BTW that class has only default constructor implemented at this time. Help solving this puzzle will be appreciated. Cheers Vaclav

      L Offline
      L Offline
      leon de boer
      wrote on last edited by
      #2

      First you don't put the word "class" in front when using a class, the compiler already knows what IDE_USBD & IDE_HCD are. However the main problem is you can't forward declare a class and use it as a member If you don't know these are forward declarations .. you are telling compiler you have a class IDE_USBD & IDE_HCD

      class IDE_USBD;
      class IDE_HCD;

      The problem is it doesn't tell the compiler how big they are and so it can't size them to use as a member. So you need at least the class data and prototypes to be above where you try and include them into another class

      class IDE_USBD {
      // ... this classes data and at least prototypes to functions

      public:
      // lets do a prototype
      int Hello(void);
      };

      class IDE_HCD {
      // ... this classes data and at least prototypes to functions
      };

      // Class IDE_ILI9341 can now use the above two classes as the compiler can size them
      class IDE_ILI9341
      {
      public:
      IDE_HCD hcd;
      IDE_USBD usbd;
      };

      // we can put the code for IDE_USBD prototype down here
      int IDE_USBD::Hello(void) {

      }

      Now the second option is close to your original but it has advantages and disadvantages you need to weight up. That is turn the entries to pointers to the classes. The compiler will be happy because it knows the size of a pointer.

      class IDE_USBD;
      class IDE_HCD;

      class IDE_ILI9341
      {
      public:
      IDE_HCD* hcd;
      IDE_USBD* usbd;
      };

      class IDE_USB {
      };

      class IDE_HCD {
      };

      The advantages are you can have the classes in whatever order you want. You can change the class objects on the fly if you need or not even create instances of them if not required. So you get a fair amount of flexibility. The downside is you have to call the class functions by pointer hcd->function(blah blah) from within your class. That makes the code ever so fractionally slower than the other. We aren't talking very much and the flexibility sometimes makes it very attractive. The big thing in this form is that class IDE_USB and IDE_USBD will not auto create (its only a pointer after all). You need to make sure you manually create an instance of the classes to the pointer in your constructor of IDE_ILI9341. So your constructor must contain the two lines to actually create the classes to the pointers

      hcd = new IDE_HCD ( /* .. parameters it takes ..*/ );
      usbd = new IDE_USB ( /* .. parameters it takes ..*/ );

      You should also dispose of them in IDE_ILI9341 destructor. As the construction used new it becomes your responsibilit

      1 Reply Last reply
      0
      • V Vaclav_

        Never mind, instead of trying to find the bug in my code I am going to rebuild the classes, they need clean-up anyway. I have , so far , two relatively similar classes dealing with embedded processor hardware. Here is a code snippet, .... class IDE_USBD; class IDE_HCD; class IDE_ILI9341 { public: class IDE_HCD hcd; class IDE_USBD usbd(); .... If I do not include parenthesizes in implementation of class IDE_USBD I get this error IDE_ILI9341.h:371: error: field 'usbd' has incomplete type class IDE_USBD usbd; ^ exit status 1 field 'usbd' has incomplete type If I add them to class IDE_HCD hcd(); than I get this error: gpf_isr = hcd.UOTGHS_Handler; ^ IDE_ILI9341.h:2351: error: '((IDE_ILI9341*)this)->IDE_ILI9341::hcd' does not have class type hcd.HCD_Init(); ^ exit status 1 '((IDE_ILI9341*)this)->IDE_ILI9341::hcd' does not have class type Both classes have #include files before the IDE_ILI9341 gets implemented , I checked that. Now adding or removing parentheses makes it work, it ain't broke , but why are the parenthesizes needed for IDE_USBD? BTW that class has only default constructor implemented at this time. Help solving this puzzle will be appreciated. Cheers Vaclav

        G Offline
        G Offline
        Graham Breach
        wrote on last edited by
        #3

        The reason for the different error messages when you have parentheses or not are down to what you are declaring (I've removed the "class" from in front of hcd and usbd to leave the relevant parts):

        class IDE_USBD;
        class IDE_HCD;

        class IDE_ILI9341
        {
        public:
        IDE_HCD hcd;
        IDE_USBD usbd();
        ...

        Here hcd doesn't have parentheses, so it is a member variable. The compiler needs to know the size of the IDE_HDC class to store the variable in the IDE_ILI9341 class, which is why you get the "incomplete type" error. The usbd declaration does have parentheses, so it is a member function returning an instance of the IDE_USBD class. The compiler doesn't need to know the size of the IDE_USBD class in this case because it doesn't affect the amount of space taken up in the class by usbd. You will run into problems later when you try to use usbd as a variable though (because it isn't one).

        1 Reply Last reply
        0
        Reply
        • Reply as topic
        Log in to reply
        • Oldest to Newest
        • Newest to Oldest
        • Most Votes


        • Login

        • Don't have an account? Register

        • Login or register to search.
        • First post
          Last post
        0
        • Categories
        • Recent
        • Tags
        • Popular
        • World
        • Users
        • Groups