| Author |
Message |
sebmaster
Joined: 09 Mar 2008 Posts: 11 Helped: 2
|
03 Nov 2009 0:07 Really simple bitshift not working on AVR32 |
|
|
|
|
Hello,
I have an AVR32 which needs to send 21 bit words (miniumum) to a CPLD.
I intend to use the SPI bus for this and have managed to set it all up, with a word size of 11 bit.
The idea is I take an integer, take the top 11 bits, shift it left 11 places, take the top 11 bits again, then send the two values in the reverse order I got them (the SPI sends data LSB first).
However my program is not working and I can't figure out why not, looking at the SPI output on a scope the LSBs (the first 21 bits sent) are always zero.
My test value is 0xFFFFFFFF so I should have to do a 16 bit shift before the value of the lower word starts dropping below its maximum surely?
Here is my code:
| Code: |
spi_status_t response;
unsigned short word_high = (data & 0xFFE0);
data = data << 11; //shift left by 11 places to get next 11 bit word.
unsigned short word_low = (data & 0xFFE0);
response = spi_write( spi, word_low);
if( response == SPI_OK )
{ while( spi_writeEndCheck(spi) == 0){}
return spi_write( spi, word_high);
}
else
return response; |
The uC I am using is an Atmel AVR32 UC3B. The architecture is big-endian.
Can anyone see any obvious mistakes?
|
|
| Back to top |
|
 |
Google AdSense

|
03 Nov 2009 0:07 Ads |
|
|
|
|
|
|
| Back to top |
|
 |
btbass
Joined: 20 Jul 2001 Posts: 1187 Helped: 113 Location: Oberon
|
03 Nov 2009 10:59 Re: Really simple bitshift not working on AVR32 |
|
|
|
|
I assume 'unsigned short' is 16-bits?
If data is 0xffffffff, (64-bits)
Then
word_high = (unsigned short)(data & 0xffe00000);
data <<= 11;
word_low = (unsigned short)(data & 0xffe00000);
|
|
| Back to top |
|
 |
sebmaster
Joined: 09 Mar 2008 Posts: 11 Helped: 2
|
03 Nov 2009 17:56 Re: Really simple bitshift not working on AVR32 |
|
|
|
|
Hi btbass,
I made the changes as you suggested (while kicking myself hard for the 0xffe0/0xffe00000 mistake) but now both shorts show a value of 0 in the debugger.
When I alter the mask to read 0xFFE0000F the short takes a value of 15.
I am sure my device is big-endian, page 5 of this document from Atmel certainly says so: http://www.atmel.com/dyn/resources/prod_documents/doc32000.pdf, yet what with the SPI bus pushing data out LSB first (when I was sure the datasheet diagrams showed MSB first) im starting to doubt it.
Is it possible that my device could be big-endian, yet when type-casting to a smaller type the (device/compiler?) starts at the highest address (LSBs)?
EDIT: OK, I just thought what would be the result if every programming language in the world truncated the LSBs instead of the MSBs when doing a downsizing typecast (for starters half of anything I ever wrote wouldnt work!) so I think ill go alter my program before I make myself look any more stupid!
Thank you!
|
|
| Back to top |
|
 |
btbass
Joined: 20 Jul 2001 Posts: 1187 Helped: 113 Location: Oberon
|
03 Nov 2009 18:23 Re: Really simple bitshift not working on AVR32 |
|
|
|
|
Im sure the compiler should take care of the endiness?
Another approach is
word_high = (uint16_t)(0xffe0 & (data >> 16));
word_low = (uint16_t)(0xffe0 & data);
|
|
| Back to top |
|
 |
sebmaster
Joined: 09 Mar 2008 Posts: 11 Helped: 2
|
03 Nov 2009 18:37 Re: Really simple bitshift not working on AVR32 |
|
|
|
|
Hi btbass,
I think it must do. I was just confused because I was picturing the typecast truncating the 16 LSBs (I still don't know where I got that idea from).
Now I mask off all but them, shift out that value, right shift 11 places and do the same again, looking at the scope it appears to work.
The other point of confusion was the order the SPI bus uses, it is MSB first unlike I gathered before due to my previous mistake.
It appears to send data MSB first but truncates the MSBs of the value, so cuts off the top 5 bits but sends the rest MSB first when I have a word size of 11.
Now I just wish I hadn't modified my CPLD program to accept LSB first....
Thanks for your help, I dont know how long I would have been floundering around for!
|
|
| Back to top |
|
 |