DSPRelated.com
Forums

Basic C question

Started by eeh July 20, 2005
Hi,

I am a beginner to use C in TI C6000 series dsp. I have a very basic
question:

I want to read the AD converter value from address 0xc00000000. I have
written the following statements but gets compilation error.

unsigned int j;
unsigned int *i;
i=0xb0000000;//adc
for(;;)
{
  j=*i;
}

error: a value of type "unsigned int" cannot be assigned to an entity
of type "unsigned int *"

Why?

Thanks!

eeh schrieb:

> I want to read the AD converter value from address 0xc00000000. I have > written the following statements but gets compilation error. > > unsigned int j; > unsigned int *i; > i=0xb0000000;//adc
Try i=(unsigned int *)0xb0000000; [...]
> error: a value of type "unsigned int" cannot be assigned to an entity > of type "unsigned int *" >
hth, Thomas

eeh wrote:
> Hi, > > I am a beginner to use C in TI C6000 series dsp. I have a very basic > question: > > I want to read the AD converter value from address 0xc00000000. I have > written the following statements but gets compilation error. > > unsigned int j; > unsigned int *i; > i=0xb0000000;//adc
Can you do that on the DSP? In "standard" C you would have to use a MALLOC statement, or something like that, to make sure the ponter i refers to allocated memory. Are you sure the memory segment at address 0xb0000000 has been allocated by the program? BTW, why do you use 0xb... in your program when you want to read the address 0xc...?
> for(;;) > { > j=*i; > }
Seems OK to me. I tested //////////////////////////////////// unsigned int j; unsigned int *i; unsigned int m; i=&m; for (m=0;m<10;m++) { j=*i; } ///////////////////////////////////// and this code compiles and runs under C++ on the PC...
> error: a value of type "unsigned int" cannot be assigned to an entity > of type "unsigned int *" > > Why?
The lack of memory allocation puzzled me, but the error seems not to be related to that. Are you sure you read the correct memory location? Would attempts to read the wrong address generate that sort of error message? Rune
> > Can you do that on the DSP? In "standard" C you would have to > use a MALLOC statement, or something like that, to make sure > the ponter i refers to allocated memory. Are you sure the > memory segment at address 0xb0000000 has been allocated by > the program? >
As the memory section 0xc0000000 is memory mapped to outside ADC address. So I need to read the ADC value from this address.
> BTW, why do you use 0xb... in your program when you want to > read the address 0xc...?
Sorry, the AD converter address should be 0xb0000000, just typing error.
"Rune Allnor" <allnor@tele.ntnu.no> wrote in message 
news:1121852313.063184.109550@g49g2000cwa.googlegroups.com...
> > > eeh wrote: >> Hi, >> >> I am a beginner to use C in TI C6000 series dsp. I have a very basic >> question: >> >> I want to read the AD converter value from address 0xc00000000. I have >> written the following statements but gets compilation error. >> >> unsigned int j; >> unsigned int *i; >> i=0xb0000000;//adc > > Can you do that on the DSP? In "standard" C you would have to > use a MALLOC statement, or something like that, to make sure > the ponter i refers to allocated memory. Are you sure the > memory segment at address 0xb0000000 has been allocated by > the program?
Rune, I don't think there is anything in standard C that prevents you from reading from an arbitrary address like this code does. I do it all the time in my embedded. Of course, whether or not that read is meaningful or legal is another issue which the C compiler ignores--C gives you the rope to hang yourself if you want. Things like j = *(0x123456); are perfectly legal, AFAIK. To eeh, which line is the error on (almost all compilers give you the line number)? If it is on the i=0xc0000000; line, then the earlier suggestion of i=(unsigned int *)0xc0000000; should fix it.
int* ptr;
int  i;

ptr = (int*)0xb0000000; // Memory mapped register for ADC reads.

i = *ptr;

The above patch of code should do what you need.

T.


eeh wrote:
> Hi, > > I am a beginner to use C in TI C6000 series dsp. I have a very basic > question: > > I want to read the AD converter value from address 0xc00000000. I have > written the following statements but gets compilation error. > > unsigned int j; > unsigned int *i; > i=0xb0000000;//adc > for(;;) > { > j=*i; > } > > error: a value of type "unsigned int" cannot be assigned to an entity > of type "unsigned int *" > > Why? > > Thanks!

Jon Harris wrote:
> "Rune Allnor" <allnor@tele.ntnu.no> wrote in message > news:1121852313.063184.109550@g49g2000cwa.googlegroups.com... > > > > > > eeh wrote: > >> Hi, > >> > >> I am a beginner to use C in TI C6000 series dsp. I have a very basic > >> question: > >> > >> I want to read the AD converter value from address 0xc00000000. I have > >> written the following statements but gets compilation error. > >> > >> unsigned int j; > >> unsigned int *i; > >> i=0xb0000000;//adc > > > > Can you do that on the DSP? In "standard" C you would have to > > use a MALLOC statement, or something like that, to make sure > > the ponter i refers to allocated memory. Are you sure the > > memory segment at address 0xb0000000 has been allocated by > > the program? > > Rune, I don't think there is anything in standard C that prevents you from > reading from an arbitrary address like this code does. I do it all the time in > my embedded. Of course, whether or not that read is meaningful or legal is > another issue which the C compiler ignores--C gives you the rope to hang > yourself if you want. Things like j = *(0x123456); are perfectly legal, AFAIK.
I am sure you are right. I'm just puzzled not to see an allocation statement. Rune
> To eeh, which line is the error on (almost all compilers give you the line > number)? If it is on the i=0xc0000000; line, then the earlier suggestion of > i=(unsigned int *)0xc0000000; should fix it.
Rune Allnor wrote:

> > eeh wrote: > >>Hi, >> >>I am a beginner to use C in TI C6000 series dsp. I have a very basic >>question: >> >>I want to read the AD converter value from address 0xc00000000. I have >>written the following statements but gets compilation error. >> >>unsigned int j; >>unsigned int *i; >>i=0xb0000000;//adc > > > Can you do that on the DSP? In "standard" C you would have to > use a MALLOC statement, or something like that, to make sure > the ponter i refers to allocated memory. Are you sure the > memory segment at address 0xb0000000 has been allocated by > the program? > > BTW, why do you use 0xb... in your program when you want to > read the address 0xc...? >
-snip- Ignoring the incorrect typecasting (which not all compilers will complain about) and the 0xb... instead of 0xc..., this code is generally right. If you are addressing a memory mapped peripheral you do not want any memory allocated off the heap -- what you want is for the code to treat that peripheral as a fixed, predefined memory location in which values magically appear. -- Tim Wescott Wescott Design Services http://www.wescottdesign.com
eeh wrote:

> Hi, > > I am a beginner to use C in TI C6000 series dsp. I have a very basic > question: > > I want to read the AD converter value from address 0xc00000000. I have > written the following statements but gets compilation error. > > unsigned int j; > unsigned int *i; > i=0xb0000000;//adc > for(;;) > { > j=*i; > } > > error: a value of type "unsigned int" cannot be assigned to an entity > of type "unsigned int *" > > Why? > > Thanks! >
i = (int*) 0xb0000000; will cause your code to compile and perhaps work. i = (unsigned int *) 0xb0000000; will be more correct. But you have another error in there. A good optimizing compiler (i.e. most modern compilers), will read your ADC at the start of the for loop then assign the same value to j an infinite number of times. A really good optimizing compiler will take this code and remove the for loop entirely since j is never used outside the code. You should declare i as: volatile unsigned int * i; On a new compiler you'll save space and perhaps execution speed if you define it as volatile unsigned int * const i = (unsigned int *) 0xb0000000; This defines (if I have my syntax right) a constant pointer to a volatile unsigned integer -- most modern compilers will recognize that they can replace this with a fixed memory location and save the code to do the register indirection. If you can't write to the ADC for some reason, or if it would be meaningless to do so, you may want to define it as volatile const unsigned int * const i = (unsigned int *) 0xb0000000; This will make your compiler throw an error if you or someone else attempts to write to the ADC. -- Tim Wescott Wescott Design Services http://www.wescottdesign.com
"Tim Wescott" schrieb
> > If you are addressing a memory mapped peripheral > you do not want any memory allocated off the heap > -- what you want is for the code to treat that > peripheral as a fixed, predefined memory location > in which values magically appear. >
Wouldn't you want to plug in a "volatile" in order to tell the C compiler that these values might "magically" change? Don't know how this is with compilers for DSP, but an optimizing compiler might decide that the value in the memory location is actually constant and optimize the assignment away, no? Regards Martin