You are invited to Log in or Register a free Frihost Account!

Quick Question in C language

NewGuyinTown
 Code: int main(void) {    int lights = 0;    int note = 1;    DDRA =  0xFF;  // port A is output    DDRB &= 0x00;  // port B is input        USART_Init();  // initialize usart        while (1)    {       if (PINB & 0x01)      // button is up       {          PORTA = 0;       }              else       {       PORTA = 0xFF;              MIDI_Send(1, note%128);       MIDI_Send(0, note%128);       note++;       }          } }

So, this is part of the code I received to put into my hardware (using an ATMEL ATMEGA32) to create music, but I do not have much experience in C. I am trying to understand this code at the moment and will learn the C syntax and structure at another time.

What does a "&=" mean?
I would assume that 0x01 is a hexidecimal that is evaluated to be 1, which I believe is the value True if it is used as a Boolean value. Why PINB & 0x01? Evaluating this with Boolean Algebra, wouldn't that be the same as PINB?
eepman
& is a bitwise AND ,when combined with an = it puts the result in the original. It combines the state of the register pins and the hexidecimal 0x01. So for instance if the register DDRA is set to 0x03 (00000011) and you "&=" with 0x01 (00000001) then only those bits which are the same (the right most one) will be put into the original, in this case 0x01. This is used to turn pins on and off.

So the statement
 Code: DDRB &= 0x00;
will turn off the Data Direction Register B (setting it to input) for every pin. This is because a Bitwise AND with 0x00 returns 0 for every bit because 1 & 0 = 0.

Hope this makes it easier to grasp
Indi
(FYI, that is flawed C syntax. That program is not legal in modern C. It might just be because of the missing parts, if this is only part of the program.)

"x @= y" is shorthand for "x = x @ y". So "DDRB &= 0x00;" is equivalent to "DDRB = DDRB & 0x00;" which is a very peculiar thing to do. It's probably just a typo for "DDRB = 0x00;".

There are two types of boolean operators in C, logical and bitwise. The logical operator for AND is && and the bitwise AND operator is &.

In C, any non-zero value is TRUE, only zero is FALSE. You can't predict exactly what value TRUE is going to be after any given operation - you only know it's not 0.

So when you do A && 1, the 1 is TRUE. If A is 0 (FALSE), the result of that operation is FALSE (0). If A is any non-zero number (TRUE), the result of that operation is a non-zero number (TRUE) - but not necessarily A or 1. So PINB && 0x01 will equal PINB only if PINB is zero. If PINB is non-zero, the value is unspecified, except that it will not be zero.

The bitwise boolean operators allow for boolean operations on a number of boolean values at the same time - where each boolean value is an individual bit. Imagine you're dealing with 8 bit numbers, which means 0x01 is 00000001 in binary (each digit is a bit). Imagine PINB is 11110000. In that case PINB & 0x01 is:
 Code: 1 1 1 1 0 0 0 0 & 0 0 0 0 0 0 0 1 -----------------   0 0 0 0 0 0 0 0

Each bit gets ANDed individually. If PINB were 00001111, it would be:
 Code: 0 0 0 0 1 1 1 1 & 0 0 0 0 0 0 0 1 -----------------   0 0 0 0 0 0 0 1

Note that the result is TRUE (non-zero) if and only if the first bit is set. If you had used 0x02 (00000010) instead of 0x01, you would be testing the second bit, 0x04 (00000100) for the third and so on.

You can also use & to test multiple bits - which is useful for checking flags from a status register.
Nyizsa
 Indi wrote: "DDRB &= 0x00;" is equivalent to "DDRB = DDRB & 0x00;" which is a very peculiar thing to do. It's probably just a typo for "DDRB = 0x00;".

I was taught to use bitwise operations instead of transferring a value into a variable, because they are faster. So it may be a faster way to zero DDRB. I don't think it has any significance nowadays, though.
Indi
Nyizsa wrote:
 Indi wrote: "DDRB &= 0x00;" is equivalent to "DDRB = DDRB & 0x00;" which is a very peculiar thing to do. It's probably just a typo for "DDRB = 0x00;".

I was taught to use bitwise operations instead of transferring a value into a variable, because they are faster. So it may be a faster way to zero DDRB. I don't think it has any significance nowadays, though.

No, it has no significance. In fact, it's a bad idea. When you write "DDRB = 0", the compiler is free to implement that any way it sees fit. If it's faster to actually move a zero value around in memory, it can do that. If it's faster to AND with 0, it can do that. If it's faster to XOR it with itself, it can do that. If there's actually an opcode on the platform to zero a value, it can do that. Whatever the case, the compiler will do what's best.

Even the simplest of compilers is sophisticated enough that the days of having to think like a CPU when writing code are pretty much over. Instead, write code for clarity, so that both other programmers and the compiler can understand best what you're trying to do. When you do that, your code will be easier to understand by you and by others, which has the side benefit of making it less likely to be buggy. On top of that, the better the compiler understands what you're trying to do, the better a job it can do optimizing. "x = 0" and "x &= 0" do the same thing, but the first one is much, much more obviously just zeroing x - which means the compiler is much, much more likely to recognize that and optimize it accordingly.
NewGuyinTown
Thanks... Didn't know there were logic operators on separate bits... So used to && as AND (and || as OR) that compares two boolean in JAVA... It made me thought that the & in C is equivalent to the && in JAVA (and I didn't see && used anywhere in the code)...

So while I was programming this device... Something struck my head... There was no memory or hard drive space on this device. I was wondering if I can still store notes (arrays of hexdecimal numbers) on this ATMEGA32 chip (40 pins: 20 on the left and 20 on the right).
Indi
 NewGuyinTown wrote: Thanks... Didn't know there were logic operators on separate bits... So used to && as AND (and || as OR) that compares two boolean in JAVA... It made me thought that the & in C is equivalent to the && in JAVA (and I didn't see && used anywhere in the code)...

As far as i remember, Java has the same operators as C, except C doesn't have >>> or instance_of. Java also has both logical (!, && and ||) and bitwise (~, & and |) boolean operators.

 NewGuyinTown wrote: So while I was programming this device... Something struck my head... There was no memory or hard drive space on this device. I was wondering if I can still store notes (arrays of hexdecimal numbers) on this ATMEGA32 chip (40 pins: 20 on the left and 20 on the right).

*shrugs* If there are no registers, i can't see how. But that's for someone else to answer.
NewGuyinTown
I downloaded the compiler (WinAVR's Programmers Notepad 2) I used at the engineering trailer... Those settings seem so confusing to configure. It's seems more like a hardware compilers/tool anyways.

So, I decide to do software programming back at my residence hall. Just want to know what compilers you would recommend me to use. I know someone is going to post a link to a list of free compiler, but I want to know what is your TOP 3 compilers you recommend. If possible, can you sort it in a way that the most highly recommended compiler to the least.
toasterintheoven
Those are bitwise operations, you need to understand those pretty well before you try doing anything with that c program, wouldn't want it doing anything off if you just have one bit off for instance, everything could start sounding like they was from bizarro land