5

I'm currently attempting to take the code library written for the Arduino USB Host shield and decouple it from the Arduino core libraries so that I can use the code in a non-Arduino microcontroller project.

From looking at the code, there aren't a lot of hard dependencies on the Arduino code base, but I'm running into some weird errors that are probably due to the differences between the Arduino build system and the LUFA build system. Specifically, I'm getting the following error in about 75% of the header files, several dozen times each:

error: expected '=', ',', ';', 'asm' or '__attribute__' before '<' token

Sometimes, the error indicates different tokens in the error, but it's still the same error. I've found a lot of similar issues in various forums and on Stack Overflow, but the solution tends to be different every time.

To be clear, this code compiles 100% fine within the Arduino build system, but these errors occur when I try to build directly with WinAVR, using the LUFA template makefiles. From looking through the code, I have determined that I needed to #define a few values, such as -DARDUINO=102 (or at least some value >=100, but the version of the Arduino IDE I'm using is 1.0.2, so I figured that was a good value to use).

So I suppose I'm looking for someone familiar with the Arduino build system to help me figure out what I'm missing. The full code library can be found here, but for the sake of providing a simple example that demonstrates the problem without including the entire code library, here's printhex.h:

#if !defined(__PRINTHEX_H__)
#define __PRINTHEX_H__

#if defined(ARDUINO) && ARDUINO >=100
#include "Arduino.h"
#else
#include <WProgram.h>
#endif

template <class T>
void PrintHex(T val)
{
    T mask = (((T)1) << (((sizeof(T) << 1) - 1) << 2));

    while (mask > 1)
    {
        if (val < mask)
            Serial.print("0");

        mask >>= 4;
    }
    Serial.print((T)val, HEX);
}

template <class T>
void PrintHex2(Print *prn, T val)
{
    T mask = (((T)1) << (((sizeof(T) << 1) - 1) << 2));

    while (mask > 1)
    {
        if (val < mask)
            prn->print("0");

        mask >>= 4;
    }
    prn->print((T)val, HEX);
}

template <class T>
void PrintBin(T val)
{
    for (T mask = (((T)1) << (sizeof(T) << 3)-1); mask; mask>>=1)
        if (val & mask)
            Serial.print("1");
        else
            Serial.print("0");
}

#endif

I should note that I do have Arduino.h copied to my include path, and that if I include Arduino.h into my main .c file, it compiles fine, so the issue isn't there. Including printhex.h, however, produces the following:

In file included from MIDI.c:38:
Lib/HostShield/printhex.h:26: error: expected '=', ',', ';', 'asm' or '__attribute__' before '<' token
Lib/HostShield/printhex.h:41: error: expected '=', ',', ';', 'asm' or '__attribute__' before '<' token
Lib/HostShield/printhex.h:56: error: expected '=', ',', ';', 'asm' or '__attribute__' before '<' token
make: *** [MIDI.o] Error 1

Lines 26, 41, and 56 are the 3 instances of the following:

template <class T>

I'm stumped. How can I solve this problem?

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
qwertymodo
  • 435
  • 7
  • 16

1 Answers1

10

You're trying to compile C++ code as C. You can (usually) do the reverse, but you need to rewrite this as plain C or use a C++ compiler (avr-g++, it appears). Changing your files to .cpp may tell the build system to use a C++ compiler automatically.

Kevin
  • 53,822
  • 15
  • 101
  • 132
  • 1
    Probably he is using `avr-gcc`. There is then of course a `avg-g++` - at least it is in my toolchain. – Patrick B. Feb 15 '13 at 19:17
  • I didn't write this, and it compiles 100% in the Arduino IDE, which uses a slightly older build of WinAVR than I am using. – qwertymodo Feb 15 '13 at 19:17
  • 1
    @qwertymodo: Nobody said anything about whether or not you wrote it, whether you're using an IDE, or whether a version is older. Are you using a C compiler to compile C++ code? It's ultimately up to you to verify or deny this. – GManNickG Feb 15 '13 at 19:19
  • I'm currently digging through the LUFA makefiles to see whether or not they are calling the C++ compiler. I can't confirm whether or not it is doing so, but there are a lot of references to configurations for C++ compilation. Anybody more familiar than I am with the LUFA build system (synced with the git trunk about 2 weeks ago, if that makes any difference) could say with more certainty. – qwertymodo Feb 15 '13 at 19:23
  • Ok, the LUFA build system definitely supports C++, but you got me on the right track. Looks like the makefiles weren't properly detecting the presence of C++ code and were, in fact, attempting to compile as C. Changing my main code file to a .cpp seems to have fixed that. I'm now getting a bunch of much more understandable errors related to missing files and undeclared names, which is totally to be expected as it's referencing the Arduino core, which I'm attempting to decouple from. Thanks for pointing me in the right direction, I think this is solved :) – qwertymodo Feb 15 '13 at 19:30
  • 1
    @qwertymodo "Looks like the makefiles weren't properly detecting the presence of C++ code" <- yes they were. If you name your file "foo.c", don't expect it to be treated as C++ (good advice for the future). –  Feb 15 '13 at 19:51
  • @H2CO3, there are .cpp files in the project that were not detected. I wasn't able to make it compile the project as C++ until I made the main file a .cpp. – qwertymodo Feb 15 '13 at 20:44