Hi all,
I've found that the "[b]_BV()[/b]" macro fails if the bit position is larger than 14.
This is because the _BV macro is defined wrong.
If you want to fix yours, locate the file [b]sfr_defs.h[/b] in your AVR toolchain. Around line 208 in the file (varies depending on which version of GCC you have in your toolchain), locate the line highlighted in red:
[b]/** \def _BV
\ingroup avr_sfr
\code #include <avr/io.h>\endcode
Converts a bit number into a byte value.
\note The bit shift is performed by the compiler which then inserts the
result into the code. Thus, there is no run-time overhead when using
_BV(). */
[color=red]#define _BV(bit) (1 << (bit))[/color]
/*@}*/[/b]
Change that line to this (the change is highlighted in red):
** **#define _BV(bit) (1[color=red]ULL[/color] << (bit))** **
That is, add "ULL" after the "1".
The reason the original fails is that "1" all by itself in a define is an INT, and being a signed 16 bit number cannot be shifted left more than 14 times without trashing it's value.
Changing it explicitly to "1ULL" makes in an unsigned long-long (i.e. a 64 bit number) which can accurately shift left up to 63 bits.
The error shows itself in code such as this:
// send 32 bit frequency tuning word
for (n = 0; n < 32; n++) {
(_freq & _BV(n)) ? *_DATA_PORT |= _DATA_BIT : *_DATA_PORT &= ~_DATA_BIT; // send a bit
*_CLOCK_PORT |= _CLOCK_BIT; // clock it in
*_CLOCK_PORT &= ~_CLOCK_BIT;
}
The value of "_BV(n)" fails when "n" is larger than 14, which makes the code fail. Patching the _BV macro fixes the problem.
Hope this helps someone.....