Yahoo Groups archive

AVR-Chat

Index last updated: 2026-04-28 22:41 UTC

Thread

What does this error mean?

What does this error mean?

2005-02-22 by kc9dag

I've done all my previous AVR programing in ASM and I program in C# 
on a daily basis so I figured I should finally learn C for the 
AVR...  Things have been going fine and now I am getting the 
following error:

Datalogger.c: In function `main':
Datalogger.c:48: error: redeclaration of 'inty' with no linkage
Datalogger.c:48: error: previous definition of 'inty' was here
Datalogger.c:48: error: parse error before '<' token
Datalogger.c:48: error: parse error before ')' token
Datalogger.c:48: warning: unused variable `inty'

for this chunk of code:

45  for(unsigned int x = 0; x <= pagecount; x++)
46  {
47  	Page_To_Buffer(x, 1);
48  	for(unsigned int inty = 0, inty < 0xFF; inty++)
49  	{
50  		sendChar(Buffer_Read_Byte(1, inty));
51  	}
52  }

I don't understand the "redeclaration of 'inty' with no linkage" when 
inty only exist in this piece of code;
I'm guessing the my C# is messing me up and I am declaing this wrong, 
but then I'm not sure why the for x chunk is not erroring out.

Thanks,
Daniel

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Leon Heller

----- Original Message ----- 
Show quoted textHide quoted text
From: kc9dag
To: AVR-Chat@yahoogroups.com
Sent: Tuesday, February 22, 2005 5:45 PM
Subject: [AVR-Chat] What does this error mean?



I've done all my previous AVR programing in ASM and I program in C#
on a daily basis so I figured I should finally learn C for the
AVR...  Things have been going fine and now I am getting the
following error:

Datalogger.c: In function `main':
Datalogger.c:48: error: redeclaration of 'inty' with no linkage
Datalogger.c:48: error: previous definition of 'inty' was here
Datalogger.c:48: error: parse error before '<' token
Datalogger.c:48: error: parse error before ')' token
Datalogger.c:48: warning: unused variable `inty'

for this chunk of code:

45  for(unsigned int x = 0; x <= pagecount; x++)
46  {
47        Page_To_Buffer(x, 1);
48        for(unsigned int inty = 0, inty < 0xFF; inty++)
49        {
50              sendChar(Buffer_Read_Byte(1, inty));
51        }
52  }

I don't understand the "redeclaration of 'inty' with no linkage" when
inty only exist in this piece of code;
I'm guessing the my C# is messing me up and I am declaing this wrong,
but then I'm not sure why the for x chunk is not erroring out.

Which compiler?

It looks like the ANSI C you are using isn't liked by your compiler. Try 
using old-fashioned K&R C.

Leon 



-- 
No virus found in this outgoing message.
Checked by AVG Anti-Virus.
Version: 7.0.300 / Virus Database: 266.3.0 - Release Date: 21/02/2005

Re: What does this error mean?

2005-02-22 by kc9dag

> line 48's accidental comma instead of a semicolon 

> Paul Colin Gloster

okay, that was the problem... I feel stupid now (I know I looked that 
code over for a hour and never noticed that comma... I've done that 
before in C# but it gives much more helpful error messages 
(like "semicolon missing" or something similar).
Thanks!!!!

Daniel

Re: What does this error mean?

2005-02-22 by kc9dag

Okay, after getting my code to work (or at least compile, I haven't 
flashed it yet) and reading all the responses I have a new but 
related question:

I'm used to working on computers with large amounts of memory and 
processor speed, so I natually used my standared for loop 
declaration: 
for(type var = constant; condition; var++){}

is this going to cause me problems on the memory limited AVR?  Should 
I get in the habit of delairing my variable before hand (I was always 
taught this was a bad thing on higher languages which have built in 
memory management) when I program for the AVRs?

BTW: I am using the gcc compiler.

Thanks,
Daniel

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Paul Colin Gloster

On Tue, Feb 22, 2005 at 05:45:22PM -0000, kc9dag wrote:


"[..] Things have been going fine and now I am getting the 
following error:

Datalogger.c: In function `main':
Datalogger.c:48: error: redeclaration of 'inty' with no linkage
Datalogger.c:48: error: previous definition of 'inty' was here
Datalogger.c:48: error: parse error before '<' token
Datalogger.c:48: error: parse error before ')' token
Datalogger.c:48: warning: unused variable `inty'

for this chunk of code:

45  for(unsigned int x = 0; x <= pagecount; x++)
46  {
47  	Page_To_Buffer(x, 1);
48  	for(unsigned int inty = 0, inty < 0xFF; inty++)
49  	{
50  		sendChar(Buffer_Read_Byte(1, inty));
51  	}
52  }

[..]"

I do not know what would happen if you would try line 48's accidental 
comma instead of a semicolon in C#, but in Java you would be saved with an 
error message and in ex-ANSI C (C89) that error would get through and 
wreak havoc at runtime so consider yourself lucky that your AVR C compiler 
caught that warning.

For clarity's sake: replace line 48 with
      for(unsigned int inty = 0; inty < 0xFF; inty++)

Regards,
Paul Colin Gloster

P.S. In future you might try programming in C++, so do not use 
postoperators as in inty++ when a preoperator is equivalent (i.e. in this 
case ++inty) because in C++ for nonprimitive types (though unsigned int 
is primitive, it is a habit not to encourage), postincrement can be 
more expensive.

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Robert Adsett

At 05:45 PM 2/22/05 +0000, kc9dag wrote:
>I've done all my previous AVR programing in ASM and I program in C#
>on a daily basis so I figured I should finally learn C for the
>AVR...  Things have been going fine and now I am getting the
>following error:
>
>Datalogger.c: In function `main':
>Datalogger.c:48: error: redeclaration of 'inty' with no linkage
>Datalogger.c:48: error: previous definition of 'inty' was here
>Datalogger.c:48: error: parse error before '<' token
>Datalogger.c:48: error: parse error before ')' token
>Datalogger.c:48: warning: unused variable `inty'
>
>for this chunk of code:
>
>45  for(unsigned int x = 0; x <= pagecount; x++)

This would be valid C++ but not C

>46  {
>47      Page_To_Buffer(x, 1);
>48      for(unsigned int inty = 0, inty < 0xFF; inty++)

This would be valid C++ but not C

>49      {
>50              sendChar(Buffer_Read_Byte(1, inty));
>51      }
>52  }


Two ways of doing this in C.  Either at the top of the function

void func( void)
{
unsigned int x, inty;


Or in the enclosing loop (this is done far less often)

void func( void)
{
unsigned int x;

<code deleted>

for(x = 0u; x <= pagecount; x++)
        {
          unsigned int inty;

         Page_To_Buffer(x, 1);
         for(inty = 0u, inty < 0xFFu; inty++)
                   {
                 sendChar(Buffer_Read_Byte(1, inty));
                    }
          }

As to why the first for loop isn't giving an error, I don't know but I 
suspect that if you fix the inner loop, you'll suddenly find the outer loop 
now complains.

A copy of K&R or Harbison &  Steele  wouldn't go awry for covering these 
sort of details.

Robert

" 'Freedom' has no meaning of itself.  There are always restrictions,
be they legal, genetic, or physical.  If you don't believe me, try to
chew a radio signal. "

                         Kelvin Throop, III

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Paul Colin Gloster

On Tue, Feb 22, 2005 at 05:57:59PM -0000, Leon Heller wrote:

"Which compiler?

It looks like the ANSI C you are using isn't liked by your compiler. Try 
using old-fashioned K&R C."

Yikes no! That would make things worse. From item 12 on
WWW.computing.DCU.Ie/~cdaly/projects/ :
"C++ Program checker
Java had a number of small improvements to C++ (as well as a number of 
big ones). These include

a. Insisting that a boolean value or expression be used in a conditional 
test e.g. if(x) becomes if(x != 0). 
b. The comma operator has been removed, so you can't write the compile 
nonsense while(i=0, i<10, i++). 
c. You cannot use uninitialised variables. 
Write a Java program that parses a C++ program and identifies if it 
breaks any of the above rules."

Though Charlie Daly was specifically talking about C++ there, everything 
in that quotation applies equivalently to C89 and K&R C. Can you actually 
think of any time K & R C would be a good choice if C89 or C99 are 
available for the same target?

Regards,
Colin Paul

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Mike Murphree

Leon Heller said:
>
> ----- Original Message -----
> From: kc9dag
> To: AVR-Chat@yahoogroups.com
> Sent: Tuesday, February 22, 2005 5:45 PM
> Subject: [AVR-Chat] What does this error mean?
>
>
>
> I've done all my previous AVR programing in ASM and I program in C# on a
> daily basis so I figured I should finally learn C for the
> AVR...  Things have been going fine and now I am getting the
> following error:
>
> Datalogger.c: In function `main':
> Datalogger.c:48: error: redeclaration of 'inty' with no linkage
> Datalogger.c:48: error: previous definition of 'inty' was here
> Datalogger.c:48: error: parse error before '<' token
> Datalogger.c:48: error: parse error before ')' token
> Datalogger.c:48: warning: unused variable `inty'
>
> for this chunk of code:
>
> 45  for(unsigned int x = 0; x <= pagecount; x++)
> 46  {
> 47        Page_To_Buffer(x, 1);
> 48        for(unsigned int inty = 0, inty < 0xFF; inty++)
> 49        {
> 50              sendChar(Buffer_Read_Byte(1, inty));
> 51        }
> 52  }
>
> I don't understand the "redeclaration of 'inty' with no linkage" when
> inty only exist in this piece of code;
> I'm guessing the my C# is messing me up and I am declaing this wrong,
> but then I'm not sure why the for x chunk is not erroring out.

What evilness allows you define variables inside a for loop structure
like that?

Take them out, and precede this code with:

unsigned int x, inty;

Mike

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Robert Adsett

At 01:05 PM 2/22/05 -0500, Robert Adsett wrote:
> >45  for(unsigned int x = 0; x <= pagecount; x++)
>
>This would be valid C++ but not C

My mistake, it appears C99 introduced this form.

Nice catch on the semicolon.

Robert

" 'Freedom' has no meaning of itself.  There are always restrictions,
be they legal, genetic, or physical.  If you don't believe me, try to
chew a radio signal. "

                         Kelvin Throop, III

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Paul Colin Gloster

On Tue, Feb 22, 2005 at 01:05:49PM -0500, Robert Adsett wrote:

"At 05:45 PM 2/22/05 +0000, kc9dag wrote:
[..]
>
>for this chunk of code:
>
>45  for(unsigned int x = 0; x <= pagecount; x++)

This would be valid C++ but not C"

Actually this is valid ANSI C (C99), but not valid ex-ANSI C (C89) nor 
valid K & R C.

">46  {
>47      Page_To_Buffer(x, 1);
>48      for(unsigned int inty = 0, inty < 0xFF; inty++)

This would be valid C++ but not C"

How so?

"[..]

A copy of K&R or Harbison &  Steele  wouldn't go awry for covering these 
sort of details."

Such books could leave someone misinformed and out of date, though 
actually I am ignorant of Harbison & Steele so if their book was 
published this decade it may be current.

Regards,
Colin Paul

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Paul Colin Gloster

On Tue, Feb 22, 2005 at 12:07:41PM -0600, Mike Murphree wrote:

"What evilness allows you define variables inside a for loop structure
like that?

Take them out, and precede this code with:

unsigned int x, inty;
"

One correct answer to the question is ANSI C. In ANSI C++ and Java at 
least, as was probably the rationale for ANSI C, the idea is to not pay 
for a variable you never use if a particular run of the program does not 
reach that loop.

Incidentally, at least in C89 would Mike's example not run the risk of x 
and inty having different datatypes?
unsigned int x;
unsigned inty;
would be safer.

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Robert Adsett

At 07:30 PM 2/22/05 +0100, Paul Colin Gloster wrote:
>Incidentally, at least in C89 would Mike's example not run the risk of x
>and inty having different datatypes?

No

Robert


" 'Freedom' has no meaning of itself.  There are always restrictions,
be they legal, genetic, or physical.  If you don't believe me, try to
chew a radio signal. "

                         Kelvin Throop, III

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Robert Adsett

At 07:16 PM 2/22/05 +0100, Paul Colin Gloster wrote:
>On Tue, Feb 22, 2005 at 01:05:49PM -0500, Robert Adsett wrote:
>"At 05:45 PM 2/22/05 +0000, kc9dag wrote:
>[..]
> >
> >for this chunk of code:
> >
> >45  for(unsigned int x = 0; x <= pagecount; x++)
>
>This would be valid C++ but not C"
>
>Actually this is valid ANSI C (C99), but not valid ex-ANSI C (C89) nor
>valid K & R C.

So I belatedly realized.  I'm not sure it's an improvement, but that's 
another issue entirely.  The question is whether the possible improvement 
in locality outweighs the possible obscurity in local declaration. I'll 
reserve judgement on that.

>A copy of K&R or Harbison &  Steele  wouldn't go awry for covering these
>sort of details."
>
>Such books could leave someone misinformed and out of date, though
>actually I am ignorant of Harbison & Steele so if their book was
>published this decade it may be current.


I don't know if they've been updated to cover C99 or not.  They were 
updated to cover C89 and I don't believe any valid C89 constructs have been 
invalidated.  I don't think there is much risk in either of them.  There 
may be more recent books.  Another item to remember is a lot of C compilers 
(particularly embedded) are barely C89 compliant never mind C99 
compliant.  Heck some of them aren't even pre-ANSI K&R complaint.

Robert

" 'Freedom' has no meaning of itself.  There are always restrictions,
be they legal, genetic, or physical.  If you don't believe me, try to
chew a radio signal. "

                         Kelvin Throop, III

Re: [AVR-Chat] Re: What does this error mean?

2005-02-22 by Robert Adsett

At 06:33 PM 2/22/05 +0000, kc9dag wrote:
>I'm used to working on computers with large amounts of memory and
>processor speed, so I natually used my standared for loop
>declaration:
>for(type var = constant; condition; var++){}
>
>is this going to cause me problems on the memory limited AVR?  Should
>I get in the habit of delairing my variable before hand (I was always
>taught this was a bad thing on higher languages which have built in
>memory management) when I program for the AVRs?

First C doesn't have built in memory management (at least in the sense of 
C# and Java).  However var is placed on the stack (in a compliant 
compiler).  Whether it's declared at the top of the routine or in a later 
loop it still is placed on the stack and room must be reserved.  The only 
case in which there is a space saving is if you run consecutive loops with 
differently named variables AND the compiler is smart enough to re-use the 
stack space (I suspect gcc is but I don't know).  So in that case

for (int i = 0; i < x; i++) {
      }
for( int j = 0; j < x; j++) {
      }

would take no more room than

void func (void)
{
int i;

for ( i = 0; i < x; i++) {
      }
for( i = 0; i < x; i++) {
      }
}

and less room than

void func (void)
{
int i, j;

for ( i = 0; i < x; i++) {
      }
for( j = 0; j < x; j++) {
      }
}

Unless of course the compiler is smart enough to realize that it can re-use 
i as if it were j.  The basic lesson, use whichever way is clearer to 
understand when you come back to it 6 - 18 months later.

Unless you have a real space issue, let the compiler do its job.

Robert

" 'Freedom' has no meaning of itself.  There are always restrictions,
be they legal, genetic, or physical.  If you don't believe me, try to
chew a radio signal. "

                         Kelvin Throop, III

Re: [AVR-Chat] What does this error mean?

2005-02-22 by Paul Colin Gloster

On Tue, Feb 22, 2005 at 01:47:20PM -0500, Robert Adsett wrote:

"[..]
[..]  Another item to remember is a lot of C compilers 
(particularly embedded) are barely C89 compliant never mind C99 
compliant.  Heck some of them aren't even pre-ANSI K&R complaint."

Agreed :(

Re: [AVR-Chat] Re: What does this error mean?

2005-02-22 by Paul Colin Gloster

On Tue, Feb 22, 2005 at 06:33:01PM -0000, Daniel wrote:

"[..]
I'm used to working on computers with large amounts of memory and 
processor speed, so I natually used my standared for loop 
declaration: 
for(type var = constant; condition; var++){}

is this going to cause me problems on the memory limited AVR?  Should 
I get in the habit of delairing my variable before hand (I was always 
taught this was a bad thing on higher languages which have built in 
memory management) when I program for the AVRs?

[..]"

Well, suppose you have

while(!0)
{
   switch(user_input())
   {
      case CASE1:
      /*...*/
      case CASE2:
      /*...*/
      case CASE3:
         for(type var = constant; condition; var++)
         {
            /*...*/
         }
         break;
      case CASE4:
      /*...*/
   }
}

On one occassion a program containing the above is run, the for loop might 
be started several times so space is declared for var and this is not a 
waste because it is being used; but another run might never have the
opportunity to enter the loop so were all variables declared before they 
are used then memory is being wasted; and in another run perhaps the loop
is sometimes being entered but not very frequently in which case it may be 
subjective whether things balance out so as to not describe it as wasteful 
of memory.

During the composition of this email, Robert Adsett showed you another
way that declaring the variable in the for loop header can save space.

However, one valid argument in favor of wastefully declaring all variables 
in advance is that it will be easier to be confident by the time the 
end-product is delivered that it will not run out of memory at runtime 
(albeit perhaps it is using more memory than needed).

Another argument which might apply against declaring variables in the for 
loop headers is that this may be inefficient for speed (but then 
optimizing for speed is often opposed to optimizing for memory).

Daniel seemed to have been under the misimpression that C programmers 
discourage declaring in the for loop headers in order to improve speed: 
this is a legacy from very poor C compilers (many C compilers (gcc 
included) are still of inferior to what was the state of the art in 
compiler technology in the 1980's) which did not support this declaration 
style simply because the C compiler writers were not very good at writing 
compilers and nobody forced them to do it. The original ANSI C has an 
inefficient library routine which was knowingly standardized as such 
because many of the implementations of the function in draft 1980's ANSI C 
were buggy to the point of gross ineffiency, even though this function had 
originally been proposed with the motivation (and simple implementation of 
being) efficient. And years after current ANSI C was standardized in 1999, 
few ANSI C compilers have ever been released.

Re: [AVR-Chat] Re: What does this error mean?

2005-02-22 by Robert Adsett

At 08:06 PM 2/22/05 +0100, Paul Colin Gloster wrote:
>However, one valid argument in favor of wastefully declaring all variables
>in advance is that it will be easier to be confident by the time the
>end-product is delivered that it will not run out of memory at runtime
>(albeit perhaps it is using more memory than needed).
>
>Another argument which might apply against declaring variables in the for
>loop headers is that this may be inefficient for speed (but then
>optimizing for speed is often opposed to optimizing for memory).

Are you aware of any compilers that delay expanding the stack appropriately 
until the branch is taken?  I was under the (uneducated) impression that 
they generally just expanded the stack to cover the largest depth needed 
within the routine regardless of whether a path with a block local variable 
was taken.  So block locals would either be added to the end of the stack 
or form a kind of end of stack area common/overlay block.

>The original ANSI C has an
>inefficient library routine which was knowingly standardized as such
>because many of the implementations of the function in draft 1980's ANSI C
>were buggy to the point of gross ineffiency, even though this function had
>originally been proposed with the motivation (and simple implementation of
>being) efficient. And years after current ANSI C was standardized in 1999,
>few ANSI C compilers have ever been released.

library routine?  Block locals have been legal since pre-ANSI AFAIK and 
have usually not been used as a matter of clarity rather than issues of 
optimization.

Robert

" 'Freedom' has no meaning of itself.  There are always restrictions,
be they legal, genetic, or physical.  If you don't believe me, try to
chew a radio signal. "

                         Kelvin Throop, III

Re: [AVR-Chat] Re: What does this error mean?

2005-02-22 by ethan@bufbotics.org

Robert Adsett said:
> So in that case
>
>  for (int i = 0; i < x; i++) {
>        }
>  for( int j = 0; j < x; j++) {
>        }
>
>  would take no more room than
>
>  void func (void)
>  {
>  int i;
>
>  for ( i = 0; i < x; i++) {
>        }
>  for( i = 0; i < x; i++) {
>        }
>  }
>

I agree with what you're saying, but I think there's a condition you may
have omitted....


void func (void) {
{
    if (THIS_CONDITION_EVALUATES_TO_FALSE) {

        for (int i=0; i<x; i++) {
            for (int j=0; j<y; j++) {
            }
        }
    }
}

In the scenario described, you'd never push 'i' or 'j' onto the stack
unless the condition is true and the code executes.  I like to scope my
variables as close as possible to where they're needed, that way I won't
allocate memory that isn't going to be used.

And I definitely agree that a compiler should be smarter than me and it
should notice that I only use a variable as a loop index, and scope it
properly for me, but I don't know enough about compilers to say whether a
nice one like gcc does that or not.


Ethan
www.bufbotics.org

Re: [AVR-Chat] Re: What does this error mean?

2005-02-22 by David Kelly

On Tue, Feb 22, 2005 at 01:55:26PM -0500, Robert Adsett wrote:
> 
> At 06:33 PM 2/22/05 +0000, kc9dag wrote:
> >I'm used to working on computers with large amounts of memory and
> >processor speed, so I natually used my standared for loop
> >declaration:
> >for(type var = constant; condition; var++){}
> >
> >is this going to cause me problems on the memory limited AVR?  Should
> >I get in the habit of delairing my variable before hand (I was always
> >taught this was a bad thing on higher languages which have built in
> >memory management) when I program for the AVRs?

That is the right sort of question. The only way to answer it is to
study the code generated by your project for your target.

> First C doesn't have built in memory management (at least in the sense of 
> C# and Java).  However var is placed on the stack (in a compliant 
> compiler).  Whether it's declared at the top of the routine or in a later 
> loop it still is placed on the stack and room must be reserved.  The only 
> case in which there is a space saving is if you run consecutive loops with 
> differently named variables AND the compiler is smart enough to re-use the 
> stack space (I suspect gcc is but I don't know).  So in that case

I think the whole point of declaring variables inline in the newer C
specs is to hit the dumb compilers in the face with a wet mop by
defining the limited scope of the variable so that its space is
reusable.

Gcc can be quite agressive in reuse without having to be hit in the face
with a wet mop. Is good to remember "-O0" (minus oh zero) compile option
so that one's source code debugger doesn't jump all over the place and
named variables one is watching don't magically change after their last
use.

-- 
David Kelly N4HHE, dkelly@HiWAAY.net
========================================================================
Whom computers would destroy, they must first drive mad.

Re: [AVR-Chat] Re: What does this error mean?

2005-02-22 by Robert Adsett

At 02:22 PM 2/22/05 -0500, ethan@bufbotics.org wrote:
>I agree with what you're saying, but I think there's a condition you may
>have omitted....
>
>
>void func (void) {
>{
>     if (THIS_CONDITION_EVALUATES_TO_FALSE) {
>
>         for (int i=0; i<x; i++) {
>             for (int j=0; j<y; j++) {
>             }
>         }
>     }
>}


You are assuming the compiler generates different code for this case.  Have 
you verified that it does?  I would expect most compilers to generate the 
same code in either case since a) it's probably faster and b) probably less 
code room and c) has no effect on the worst case stack usage.

Robert

" 'Freedom' has no meaning of itself.  There are always restrictions,
be they legal, genetic, or physical.  If you don't believe me, try to
chew a radio signal. "

                         Kelvin Throop, III

Re: [AVR-Chat] Re: What does this error mean?

2005-02-22 by ethan@bufbotics.org

Robert Adsett said:
>       At 02:22 PM 2/22/05 -0500, ethan@bufbotics.org wrote:
>  >
>  >void func (void) {
>  >{
>  >     if (THIS_CONDITION_EVALUATES_TO_FALSE) {
>  >
>  >         for (int i=0; i             for (int j=0; j             }
>  >         }
>  >     }
>  >}
>
>
>  You are assuming the compiler generates different code for this case.
> Have
>  you verified that it does?  I would expect most compilers to generate the
>  same code in either case since a) it's probably faster and b) probably
> less
>  code room and c) has no effect on the worst case stack usage.
>


Hmm, yes, I am assuming the compiler generates different code depending
upon how the variables are scoped.  Haven't looked into it at all, in
fact, I wouldn't even know where to look to find out.  I guess the
question that comes to mind is "where does it end?"  If the compiler
chooses to allocate the memory for a loop variable, how far does the
compiler take it?  What if you've got a function that is defined but never
invoked.  Do all of the local variables from that function get defined? 
How far does it go?


Better question, how does one (me) find out what the compiler has done to
me?  I'm pretty new to microcontroller programming (used to webservers
with gigs & gigs of memory) and I quickly found out on an ATtiny26 project
that I've definitely got to pay more attention to memory usage than in the
past.  Even simple things like using 'unsigned char' rather than 'int' for
values that won't exceed 255.  That change alone saved me about 40% of the
memory on the tiny26.  Its a whole new (and exciting) world.

Ethan
www.bufbotics.org

Re: [AVR-Chat] Re: What does this error mean?

2005-02-22 by Robert Adsett

At 02:42 PM 2/22/05 -0500, ethan@bufbotics.org wrote:
>Hmm, yes, I am assuming the compiler generates different code depending
>upon how the variables are scoped.  Haven't looked into it at all, in
>fact, I wouldn't even know where to look to find out.  I guess the
>question that comes to mind is "where does it end?"  If the compiler
>chooses to allocate the memory for a loop variable, how far does the
>compiler take it?  What if you've got a function that is defined but never
>invoked.  Do all of the local variables from that function get defined?
>How far does it go?


How far does it go.  It depends on the compiler.  Some will automatically 
inline small routines especially if doing so is faster or smaller.  A good 
starting point though is the function level.  The basic requirement is the 
code must behave as if it was it was generated naively.  In some 
theoretical sense if the compiler can replace you're entire program with

:lp
         mov reg, #3
         jmp lp

and get the same result and a full 20MB program it's perfectly free to do so.

>Better question, how does one (me) find out what the compiler has done to
>me?  I'm pretty new to microcontroller programming (used to webservers
>with gigs & gigs of memory) and I quickly found out on an ATtiny26 project
>that I've definitely got to pay more attention to memory usage than in the
>past.  Even simple things like using 'unsigned char' rather than 'int' for
>values that won't exceed 255.  That change alone saved me about 40% of the
>memory on the tiny26.  Its a whole new (and exciting) world.


Have the compiler save an intermediate assembly file.  Reading those is 
usually educational.

For instance given the question at hand

Given

void func( void)
{
int j

if( some condition) {
     for( int i = 0; i < x; i++) {
          }
      }
}

The compiler could generate

;void func( void)
;{
;int j
         sub sp, #2

;if( some condition) {
         jmp condition true loopend

;    for( int i = 0; i < x; i++) {
         sub sp, #2


         add sp, #2
;         }
;     }

:loopend
         add sp, #2
;}

Or it could generate

;void func( void)
;{
;int j
         sub sp, #4

;if( some condition) {
         jmp condition true loopend

;    for( int i = 0; i < x; i++) {


;         }
;     }

:loopend
         add sp, #4
;}

The later allocating the local i whether the conditional is true or not.

Both behaviours are fully legal, both have the same maximum stack depth but 
one has twice the worst case overhead of the other while keeping the same 
best case overhead.  I know which behaviour I'd prefer.

Robert


" 'Freedom' has no meaning of itself.  There are always restrictions,
be they legal, genetic, or physical.  If you don't believe me, try to
chew a radio signal. "

                         Kelvin Throop, III

Re: [AVR-Chat] What does this error mean?

2005-04-11 by Paul Colin Gloster

On Tue, Feb 22, 2005 at 01:40:14PM -0500, Robert Adsett wrote:

"At 07:30 PM 2/22/05 +0100, Paul Colin Gloster wrote:
>Incidentally, at least in C89 would Mike's example not run the risk of x
>and inty having different datatypes?

No"

Okay.

Re: [AVR-Chat] Re: What does this error mean?

2005-04-11 by Paul Colin Gloster

On Tue, Feb 22, 2005 at 02:21:51PM -0500, Robert Adsett wrote:

"At 08:06 PM 2/22/05 +0100, Paul Colin Gloster wrote:
[..]

>The original ANSI C has an
>inefficient library routine which was knowingly standardized as such
>because many of the implementations of the function in draft 1980's ANSI C
>were buggy to the point of gross ineffiency, even though this function had
>originally been proposed with the motivation (and simple implementation of
>being) efficient. And years after current ANSI C was standardized in 1999,
>few ANSI C compilers have ever been released.

library routine?  Block locals have been legal since pre-ANSI AFAIK and 
[..]"

I was not thinking of declarations within a block. I was probably 
incompletely remembering the following thread "accu-general: Rationale 
for behaviour of strncpy() in C89/C99" on accu-general@ACCU.org :

timestamped Wed, 03 Jan 2001 08:45:47 +0000
an email from someone contained:

"Hiya!

I came across something recently which puzzled me slightly simple because I
can't work out *why* the standard was written in the way it is.  Allow me
to explain - consider the code:

	char string[16];

	memset(string, '*', sizeof(string));
	strcpy(string, "Hi");	
	strncpy(string, "Hello World", sizeof(string));

After the strcpy(),  string contains "Hi\0*************".  This seems quite
reasonable - the minimum number of bytes have been changed to copy the
string.  

After the strncpy(),  string contains "Hello World\0\0\0\0\0" - an extra 4
bytes have been assigned values by this call,  despite the fact that this
does not affect the representation of the string at all.  In this case the
speed penalty is almost negligible,  however if the array had been declared
somewhat larger,  it may become quite significant.  

C89 demands this behaviour in 7.11.2.4,  and C99 in 7.15.2.4(3).  Can
anybody explain to me what the thinking was behind the behaviour of
strncpy(),  and why the other strn...() functions [and snprintf()] don't
have the same behaviour?

Wishing you a Bug-free New Year..."


followed by an email from Jim Hyslop <Jim.Hyslop@Leitch.com>
time stamped Wed, 3 Jan 2001 09:33:58 -0500 :

"Well, as I understand it (and I may be perpetuating an urban legend) the
current, standard behaviour of strncpy is actually a bug. When the function
was originally written, it didn't behave the way it was *supposed* to
behave. But some programs got written to depend on the buggy behaviour, so
the buggy behaviour became the de facto standard behaviour.

Jim"

followed by an email from another person timestamped Wed, 3 Jan 2001 10:03:08 -0800 :

"According to "Rationale for American National Standard for Information
Systems - Programming Language - C" (
http://www.lysator.liu.se/c/rat/title.html#4-11 ) 

4.11.2.4  The strncpy function
strncpy was initially introduced into the C library to deal with
fixed-length name fields in structures such as directory entries.  Such
fields are not used in the same way as strings: the trailing null is
unnecessary for a maximum-length field, and setting trailing bytes for
shorter names to null assures efficient field-wise comparisons.  strncpy is
not by origin a ``bounded strcpy,'' and the Committee has preferred to
recognize existing practice rather than alter the function to better suit it
to such use.  

[ACCU mailing list details, see http://accu.org/mailinglists.htm ]"

Re: [AVR-Chat] Re: What does this error mean?

2005-04-11 by Robert Adsett

At 12:21 PM 4/11/05 +0200, Paul Colin Gloster wrote:

>On Tue, Feb 22, 2005 at 02:21:51PM -0500, Robert Adsett wrote:
>
>"At 08:06 PM 2/22/05 +0100, Paul Colin Gloster wrote:
>[..]
>
> >The original ANSI C has an
> >inefficient library routine which was knowingly standardized as such
> >because many of the implementations of the function in draft 1980's ANSI C
> >were buggy to the point of gross ineffiency, even though this function had
> >originally been proposed with the motivation (and simple implementation of
> >being) efficient. And years after current ANSI C was standardized in 1999,
> >few ANSI C compilers have ever been released.
>
>library routine?  Block locals have been legal since pre-ANSI AFAIK and
>[..]"
>
>I was not thinking of declarations within a block. I was probably
>incompletely remembering the following thread "accu-general: Rationale
>for behaviour of strncpy() in C89/C99" on accu-general@ACCU.org :
>
>timestamped Wed, 03 Jan 2001 08:45:47 +0000
>an email from someone contained:
>
>"Hiya!
>
>I came across something recently which puzzled me slightly simple because I
>can't work out *why* the standard was written in the way it is.  Allow me
>to explain - consider the code:
>
>         char string[16];
>
>         memset(string, '*', sizeof(string));
>         strcpy(string, "Hi");
>         strncpy(string, "Hello World", sizeof(string));
>
>After the strcpy(),  string contains "Hi\0*************".  This seems quite
>reasonable - the minimum number of bytes have been changed to copy the
>string.
>
>After the strncpy(),  string contains "Hello World\0\0\0\0\0" - an extra 4
>bytes have been assigned values by this call,  despite the fact that this
>does not affect the representation of the string at all.  In this case the
>speed penalty is almost negligible,  however if the array had been declared
>somewhat larger,  it may become quite significant.

OK, that makes more sense, on the other hand there are a lot of other 
string and memory copy library routines without that behaviour and if they 
don't fit it's easy enough to write a routine that matches strncpy in every 
respect other than padding the string length with 0's.  Also as pointed out 
it wasn't a bug.  The original was introduced for directory manipulation.

Robert



" 'Freedom' has no meaning of itself.  There are always restrictions,   be 
they legal, genetic, or physical.  If you don't believe me, try to chew a 
radio signal. "  -- Kelvin Throop, III
http://www.aeolusdevelopment.com/

Move to quarantaine

This moves the raw source file on disk only. The archive index is not changed automatically, so you still need to run a manual refresh afterward.