I am facing a problem in using the right shift operator in C with keil. The instruction is:for(i=0;i<=8;i++) { j=sum>>i; } where sum= 32 bit no. the instruction is not executed if the syntax is as shown above. but if i write a numerical value instead of using the variable name 'sum' then the instruction is easily executed. i need to use the variable name only. how do i fix this problem?
this is the actual code i am referring to:
#include<stdio.h> #include<intrins.h> #include<absacc.h> #include<math.h> #include<reg51.h> int count; /* holds counter value*/ int arr[15]; /* array to store 15 nos.*/ int avg; /* average of 15 nos. */ long int sum; /* sum of 15 nos. (16 bit)*/ void main() { int i,j; /* variable initialization */ sum=0x00; /* initial value*/ count=0x00; /* initial value*/ #pragma asm /* entering 15 nos into memory locations*/ mov r2, #0fh mov dptr, #3000h mov a, #21h up1:movx @dptr, a inc dptr inc a djnz r2,up1 mov r3, #0fh /* retreiving data from memory and storing 15 nos in array*/ mov dptr, #3000h up2: movx a, @dptr mov b, a #pragma endasm arr[count]=ACC; count++; #pragma asm inc dptr djnz r3,up2 #pragma endasm for(count=0;count<=15;count++) /* adding 15 nos. */ { sum=sum+arr[count]; /* sum */ } avg=sum / 0x0f; /* average of 15 nos. */ P2=avg; ACC=sum; /*moving lsb 8 bits of 16 bit sum on port 0 */ P0=ACC; for(i=0;i<=8;i++) { j=sum>>i; /*moving msb 8 bits of 16 bit sum on port 1*/ } B=j; P1=B; }
here i am not able to divide neither am i able to right shift the data when i use the variable name sum
"it doesnt work"
You haven't actually stated what it is supposed to do yet! What is it, exactly, that you are trying to achieve?
"How about posting the assembly code output from the .cod file in both cases?"
Before posting any more code, please take care to read the Notes immediately above the 'Message' window when you post - they tell you what to do to have your code appear properly formatted (as in Drew's post).
Note that the .cod file is generated by the LX51 Linker, and shows the result of Linker optimisations; you also need to show the Compiler listing (.lst) to see what the compiler actually generated...
i tried doing this but it doesnt work.
here sum is defined as long int in the code. hence it can have a 32 bit value. but in the present case 'sum' holds a 16 bit value only. the problem is: the instruction for right shift is not executed if the syntax is as follows: for(i=0;i<=8;i++) { j=sum>>i; } but the instruction is executed if the syntax is as follows: for(i=0;i<=8;i++) { j=0x0258>>i; } i.e. the instruction is not executed if i am using the variable name 'sum' but if i put a numerical value instead of 'sum' then it is easily executed. how do i fix this problem?
My interpretation of the original post is that he wants to do something to each of the least significant 8 bits one at a time.
for (i = 0; i < 8; ++i) { bit = (sum >> i) & 1; DoSomething(bit); // called for bit 0, bit 1... bit 7 }
This should work, though it's a little inefficient because it shifts too much. It also shifts a U32 unnecessarily, which will take time on an 8051. I'd probably write code more like:
U8 temp = (U8)sum; for (i = 0; i < 8; ++i) { DoSomething (temp & 1); temp >>= 1; }
so that you only have to shift an 8-bit quantity, and you only do 8 1-bit shifts.
So, if my interpretation of the OP is correct, the question is why (sum >> i) doesn't work in the posted code, though (sum >> 1) does.
How about posting the assembly code output from the .cod file in both cases?
Try this
sum >>= 8; // right justify by 8 bit positions
or create a union
where sum= 32 bit no. what i want to do is bring the msb 8 bits of the 16 bit value in the variable sum to the lsb position.
I didn't catch the information whether the sum is a 32bit or 16bit number.And the result you want to get.
You'd better draw a simple figure to present your problem clearly. Just like: +0 1 2 3 4 5 6 7 8 9 a b c d e f+ | | |
...............
sum>>=8
can you please elaborate further. what i want to do is bring the msb 8 bits of the 16 bit value in the variable sum to the lsb position. so i have to shift right 8 times and so the loop is used
look at the code. loop 1 shifts sum 0 bits. loop 2 shifts sum 1 bit. loop 3 shifts sum 2 more bits. and so on. The constant is restored each time. you most likly want sum >> 1
View all questions in Keil forum