Switching between bit number and binary definition.

Change between bit number and binary definition,
this is from the code for the MPU-6050. Can someone
clarify what is going on with this part a little more?
Im confused with what the comments are saying.

Is for exampe bit(MPU6050_D1) => 00000001,
and bit(MPU6050_D2) => 00000010 ?

// Defines for the bits, to be able to change 
// between bit number and binary definition.
// By using the bit number, programming the sensor 
// is like programming the AVR microcontroller.
// But instead of using "(1<<X)", or "_BV(X)", 
// the Arduino "bit(X)" is used.
#define MPU6050_D0 0
#define MPU6050_D1 1
#define MPU6050_D2 2
#define MPU6050_D3 3
#define MPU6050_D4 4
#define MPU6050_D5 5
#define MPU6050_D6 6
#define MPU6050_D7 7

In your example, bit(MPU6050_D1) would be "00000010".

The datasheet uses the bit number for a register of the avr microcontroller.
The avr gcc compiler is like that.
Instead of using a mask, the bit number is used in the source code.

Suppose bit number 2 (the third bit, 0000 0100) should be set without changing the other bits.
Normally, this would be done: REGISTER |= 0x04; // valid, but not used
The avr gcc style is however this: REGISTER |= (1<<2); // '2' for bit number 2
There is a macro for that: REGISTER |= _BV(2);
The Arduino environment has it's own macro: REGISTER |= bit(2);
Or this: bitSet(REGISTER, 2);

Does this make any sense ?

EDIT: I had my bit numbers wrong, corrected.

I think its making sense lol. So #define MPU6050_D0 0 is defining the D0 regeister of the MPU6050 to the "integer" value of 0 which really seen as binary 0, D1 as "1" in other words 0001 and so on, is this correct?

Im having a hard time wrapping my head around these bitwise operators :smiley: 1<<2 is shift 1 over 2 so, 0001 => 0100 ( binary 1 to binary 4 )
REGISTER |= bit(2) where 2 is 0x02, and 0x02 is hex for 0010 ( 2 in binary ) ?? Not used to thinking of numbers in this manner.

Sorry. I think my examples were wrong. I have corrected it.

bit(2) is also a '1' shifted two times to get 0000 0100
http://arduino.cc/en/Reference/Bit

As I wrote, the avr chips use the bit number.
Bit number 0 is the most right bit.
Bit number 1 is the second from the right.
Bit number 2 is the third from the right.
And so on.

To convert that bit number to a binary value, all that is needed is to shift a '1' to left for the amount of the bit number.

To set bit number 2:
REGISTER |= (1 << 2)

That is why all that shifting is used. The avr chip does not do that shifting, it is done by the compiler. The result is that you only have to look for the number to know the bit number.

Background story: The avr chip has a single instruction to set or clear one bit in a register, without changing the other bits. So when REGISTER = _BV(2) is used, it will be a very fast single instruction.

Not used to thinking of numbers in this manner.

You almost certainly are, but in decimal, rather than binary. :wink:

Think back to school were you were taught

100's 10's 1's
--------------
  1   5   7

1x100 + 5x10 + 7x1 = 157
Then, instead of each column being 10 times greater than the previous one, each column is two times greater (base 2 instead of base 10) and you get

128 64 32 16 8 4 2 1
--------------------
  1  0  0  1 1 1 0 1

1x128 + 0x64 + 0x32 + 1x16 + 1x8 + 1x4 + 0x2 + 1x1 = 157

That's all binary is - counting in twos instead of tens.

Yes I understand binary, its just the meaning of the binary level operations and whats going on when you mask things, its starting to make more sense. Hopefully Ill be faster at switching between binary and decimal on the fly.

#define MPU6050_D0 0 is the same as MPU6050_D0 = 0000000
#define MPU6050_D1 1 is same as MPU6050_D0 = 00000001
.
.
.

bit(MPU6050_D1) => 00000010, thats 2. :smiley: Awesome.

Sorry to beat a dead horse here :smiley:

bit(MPU6050_D1) => 00000010, thats 2. smiley-grin Awesome.

Potentially incorrect.
In C, 00000010 = 810 :wink:

:stuck_out_tongue: Im thinking in binary. Do you mean this is 2 bits in C ?

Im thinking in binary

...but writing in octal.
A constant prefixed with a zero is taken as octal (base 8) in C.

You can't type binary numbers in C/C++ code. We use hex instead: ] :smiley:
2 => 02 => [ 00000010 ( Binary ) ]
int => octal => binary

int w = 02; //octal for 2
int x = 2; // decimal
int y = 0x2; // hex

int z = 010; // octal ( 8 )

Try and not confuse me.

borillion:
You can't type binary numbers in C/C++ code. We use hex instead: ] :smiley:
in binary 2 => 2 => [ 00000010 ( Binary ) ]

int w = 02; //octal for 2
int x = 2; // decimal
int y = 0x2; // hex

int z = 010; // octal ( 8 )

Try and not confuse me.

Yes you can:

int z = 0b00000010; // binary for 2

0hh didn't know that

borillion:
0hh didn't know that

It's a gcc extension that won't work on all compilers.
Works with avr-gcc though, which is what the Arduino IDE uses.