
I was wondering if there was any reason we avoid C99 features in u- boot source.
Specifically the ability to declare variables in the middle of functions.
There are a slew of places that we have something like:
foobar() { ...
#ifdef CONFIG_COOL_FEATURE u32 myvarrocks; #endif
...
#ifdef CONFIG_COOL_FEATURE myvarrocks = foo * bar * bar;
gd->neato = myvarrocks #endif
it would be nice to just have:
foobar() {
...
#ifdef CONFIG_COOL_FEATURE u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks #endif
- k

Dear Kumar Gala,
In message 4A0B9AAA-4714-4C27-84A7-22FCE4D91DDA@freescale.com you wrote:
I was wondering if there was any reason we avoid C99 features in u- boot source.
Specifically the ability to declare variables in the middle of functions.
One reason is that I consider such code extremely ugly and hard to read and understand.
There are a slew of places that we have something like:
...
#ifdef CONFIG_COOL_FEATURE u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks #endif
It would be even better to avoid such #ifdef's, or at least the need for such special local variables.
Best regards,
Wolfgang Denk

Hi Wolfgang,
Wolfgang Denk wrote:
Dear Kumar Gala,
In message 4A0B9AAA-4714-4C27-84A7-22FCE4D91DDA@freescale.com you wrote:
I was wondering if there was any reason we avoid C99 features in u- boot source.
Specifically the ability to declare variables in the middle of functions.
One reason is that I consider such code extremely ugly and hard to read and understand.
ACK. I don't expect to see variables spring into life in the middle of nowhere.
There are a slew of places that we have something like:
...
#ifdef CONFIG_COOL_FEATURE u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks #endif
It would be even better to avoid such #ifdef's, or at least the need for such special local variables.
Sometimes (often?) that is impossible.
Best regards,
Wolfgang Denk
If I'm not confused, I've seen block-local u-boot variables, has the advantages of being more distinctive and limits the lifetime of the variable.
#ifdef CONFIG_COOL_FEATURE { u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks } #endif
Is this an acceptable compromise?
Best regards, gvb

On Wed, Apr 8, 2009 at 2:46 PM, Jerry Van Baren gerald.vanbaren@ge.com wrote:
ACK. I don't expect to see variables spring into life in the middle of nowhere.
I don't see what's wrong with that. The advantage is that the variable is close to where it's being used, so that you can see the context more easily.
If I'm not confused, I've seen block-local u-boot variables, has the advantages of being more distinctive and limits the lifetime of the variable.
I don't see what the value is of limiting the lifetime of the variable. The compiler isn't going to use that as a hint, anyway. It's just going to use this for syntax checking. If you define and initialize a variable at the top of the function, but don't use that variable until a hundred lines later, the compiler is going to initialize the variable when it's first used, not when the function is first entered. Chances are it's not even going to define stack space for it.
#ifdef CONFIG_COOL_FEATURE { u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks } #endif
Is this an acceptable compromise?
This is what we do today, and I think it's ugly.

-----Original Message----- From: u-boot-bounces@lists.denx.de [mailto:u-boot-bounces@lists.denx.de] On Behalf Of Timur Tabi Sent: Thursday, April 09, 2009 1:55 AM To: Jerry Van Baren Cc: U-Boot-Users ML; Kumar Gala Subject: Re: [U-Boot] use of C99
On Wed, Apr 8, 2009 at 2:46 PM, Jerry Van Baren gerald.vanbaren@ge.com wrote:
ACK. I don't expect to see variables spring into life in
the middle of
nowhere.
I don't see what's wrong with that. The advantage is that the variable is close to where it's being used, so that you can see the context more easily.
If I'm not confused, I've seen block-local u-boot variables, has the advantages of being more distinctive and limits the lifetime of the variable.
I don't see what the value is of limiting the lifetime of the variable. The compiler isn't going to use that as a hint, anyway. It's just going to use this for syntax checking. If you define and initialize a variable at the top of the function, but don't use that variable until a hundred lines later, the compiler is going to initialize the variable when it's first used, not when the function is first entered. Chances are it's not even going to define stack space for it.
One of the biggest problem is uncontrolled variable definitions that gets even nasty when variables have same names with different types; though under different set of #ifdefs. Quite possible for commonly used variable names - i, ptr, tmp, etc.
I feel, here, ifdefs provide a false sense of 'enclosure' with possibility of frequent breaches - in code (while implementing) and in simple reading (for understanding).
~sanjeev
#ifdef CONFIG_COOL_FEATURE { u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks } #endif
Is this an acceptable compromise?
This is what we do today, and I think it's ugly.
-- Timur Tabi Linux kernel developer at Freescale _______________________________________________ U-Boot mailing list U-Boot@lists.denx.de http://lists.denx.de/mailman/listinfo/u-boot

Premi, Sanjeev wrote:
One of the biggest problem is uncontrolled variable definitions that gets even nasty when variables have same names with different types; though under different set of #ifdefs. Quite possible for commonly used variable names - i, ptr, tmp, etc.
Then let's just say that if you're going to define a variable in the middle of a function, it can't have the same name as another variable in that function.
I feel, here, ifdefs provide a false sense of 'enclosure' with possibility of frequent breaches - in code (while implementing) and in simple reading (for understanding).
Sorry, I don't understand what you're talking about. The #ifdefs are used to enable feature-specific code on platforms that have that feature.

-----Original Message----- From: Timur Tabi [mailto:timur@freescale.com] Sent: Thursday, April 09, 2009 2:28 AM To: Premi, Sanjeev Cc: Jerry Van Baren; U-Boot-Users ML; Kumar Gala Subject: Re: [U-Boot] use of C99
Premi, Sanjeev wrote:
One of the biggest problem is uncontrolled variable definitions that gets even nasty when variables have same names with different types; though under different set of #ifdefs. Quite possible for commonly used variable names - i, ptr, tmp, etc.
Then let's just say that if you're going to define a variable in the middle of a function, it can't have the same name as another variable in that function.
I feel, here, ifdefs provide a false sense of 'enclosure'
with possibility
of frequent breaches - in code (while implementing) and in
simple reading
(for understanding).
Sorry, I don't understand what you're talking about. The #ifdefs are used to enable feature-specific code on platforms that have that feature.
I was referring to declaring variable within #ifdefs with belief that use will be contained.
e.g. #ifdef CONFIG_COOL_FEATURE int i; int* ptr ; ... ... #endif
... ... 2 screenful down; in same function... ...
#ifdef CONFIG_HOT_FEATURE u32 i; void* ptr; ... ... #endif
Maybe for sometime the usage seems contained. Until someone decides to have both the COOL and HOT feature.
~sanjeev
-- Timur Tabi Linux kernel developer at Freescale

Premi, Sanjeev wrote:
Maybe for sometime the usage seems contained. Until someone decides to have both the COOL and HOT feature.
And that's why I said that U-Boot can allow in-function variable declarations, but all variables must have unique names. The only exception to that rule can be variables declared at the top of iterators.
That's just my two cents.

Premi, Sanjeev wrote:
-----Original Message----- From: u-boot-bounces@lists.denx.de [mailto:u-boot-bounces@lists.denx.de] On Behalf Of Timur Tabi Sent: Thursday, April 09, 2009 1:55 AM To: Jerry Van Baren Cc: U-Boot-Users ML; Kumar Gala Subject: Re: [U-Boot] use of C99
On Wed, Apr 8, 2009 at 2:46 PM, Jerry Van Baren gerald.vanbaren@ge.com wrote:
ACK. I don't expect to see variables spring into life in
the middle of
nowhere.
I don't see what's wrong with that. The advantage is that the variable is close to where it's being used, so that you can see the context more easily.
If I'm not confused, I've seen block-local u-boot variables, has the advantages of being more distinctive and limits the lifetime of the variable.
I don't see what the value is of limiting the lifetime of the variable. The compiler isn't going to use that as a hint, anyway. It's just going to use this for syntax checking. If you define and initialize a variable at the top of the function, but don't use that variable until a hundred lines later, the compiler is going to initialize the variable when it's first used, not when the function is first entered. Chances are it's not even going to define stack space for it.
One of the biggest problem is uncontrolled variable definitions that gets even nasty when variables have same names with different types; though under different set of #ifdefs. Quite possible for commonly used variable names - i, ptr, tmp, etc.
I'm showing extreme ignorance here, but does C99 let you do this?
for (int i = 0; i < x ; i++) ?
Doing a lot of C++ has rotted my brain, but this is one thing I like.
regards, Ben

-----Original Message----- From: Ben Warren [mailto:biggerbadderben@gmail.com] Sent: Thursday, April 09, 2009 2:33 AM To: Premi, Sanjeev Cc: Timur Tabi; Jerry Van Baren; U-Boot-Users ML; Kumar Gala Subject: Re: [U-Boot] use of C99
Premi, Sanjeev wrote:
-----Original Message----- From: u-boot-bounces@lists.denx.de [mailto:u-boot-bounces@lists.denx.de] On Behalf Of Timur Tabi Sent: Thursday, April 09, 2009 1:55 AM To: Jerry Van Baren Cc: U-Boot-Users ML; Kumar Gala Subject: Re: [U-Boot] use of C99
On Wed, Apr 8, 2009 at 2:46 PM, Jerry Van Baren gerald.vanbaren@ge.com wrote:
ACK. I don't expect to see variables spring into life in
the middle of
nowhere.
I don't see what's wrong with that. The advantage is that the variable is close to where it's being used, so that you can see the context more easily.
If I'm not confused, I've seen block-local u-boot
variables, has the
advantages of being more distinctive and limits the
lifetime of the
variable.
I don't see what the value is of limiting the lifetime of the variable. The compiler isn't going to use that as a hint, anyway. It's just going to use this for syntax checking. If you define and initialize a variable at the top of the function, but
don't use that
variable until a hundred lines later, the compiler is going to initialize the variable when it's first used, not when the
function is
first entered. Chances are it's not even going to define
stack space
for it.
One of the biggest problem is uncontrolled variable definitions that gets even nasty when variables have same names with different types; though under different set of #ifdefs. Quite possible for commonly used variable names - i, ptr, tmp, etc.
I'm showing extreme ignorance here, but does C99 let you do this?
for (int i = 0; i < x ; i++) ?
That's much better contained than declaring in a ifdef.
Doing a lot of C++ has rotted my brain, but this is one thing I like.
I love C++; still avoid declare as you go. Iterators (as you mention above) are only exception.
~sanjeev
regards, Ben

Timur Tabi wrote:
On Wed, Apr 8, 2009 at 2:46 PM, Jerry Van Baren gerald.vanbaren@ge.com wrote:
ACK. I don't expect to see variables spring into life in the middle of nowhere.
I don't see what's wrong with that. The advantage is that the variable is close to where it's being used, so that you can see the context more easily.
Agreed. In many cases it reduces clutter by eliminating the need for separate declaration and assignment.
I don't see what the value is of limiting the lifetime of the variable.
It frees the variable up for later such blocks to use. As does declaring iterators inside a for loop, but I guess that's forbidden as well. :-)
It's just going to use this for syntax checking. If you define and initialize a variable at the top of the function, but don't use that variable until a hundred lines later, the compiler is going to initialize the variable when it's first used, not when the function is first entered. Chances are it's not even going to define stack space for it.
Chances are it will allocate all stack space for all variables up front, regardless of where they're declared.
#ifdef CONFIG_COOL_FEATURE { u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks }
#endif
Is this an acceptable compromise?
This is what we do today, and I think it's ugly.
Yes. But not as ugly as having two #ifdef blocks.
-Scott

Scott Wood wrote:
It frees the variable up for later such blocks to use. As does declaring iterators inside a for loop, but I guess that's forbidden as well. :-)
I'm not sure whether we want to allow the same variable to be defined more than once, even with the same type, inside a function.
Chances are it will allocate all stack space for all variables up front, regardless of where they're declared.
Yes, but it many cases it won't allocate any stack space at all because it will just keep the variable in a register. My point was that if a variable is defined later in a function, then it's more likely to have limited scope, so the compiler will be more likely to use a register instead of stack to store it.
This is what we do today, and I think it's ugly.
Yes. But not as ugly as having two #ifdef blocks.
Agreed, but I don't consider it to be much of a compromise.

Timur Tabi wrote:
Scott Wood wrote:
It frees the variable up for later such blocks to use. As does declaring iterators inside a for loop, but I guess that's forbidden as well. :-)
I'm not sure whether we want to allow the same variable to be defined more than once, even with the same type, inside a function.
What's wrong with this:?
for (i = 0; i < n; i++) { int j; ... }
for (i = 0; i < m; i++) { int j; ... }
Chances are it will allocate all stack space for all variables up front, regardless of where they're declared.
Yes, but it many cases it won't allocate any stack space at all because it will just keep the variable in a register. My point was that if a variable is defined later in a function, then it's more likely to have limited scope, so the compiler will be more likely to use a register instead of stack to store it.
I don't think it will make a difference. The compiler knows what the lifetime of the variable is, regardless of where you declare it.
-Scott

Dear Timur Tabi,
In message ed82fe3e0904081325s560fb99cg83b6aaa9176cd8db@mail.gmail.com you wrote:
I don't see what's wrong with that. The advantage is that the variable is close to where it's being used, so that you can see the context more easily.
Bear with an old man like me. I am used to the habit that variables get decleared at the begin of a block, not in the middle of it. When searching for the declaration of a variable, I find it a major PITA if I have to scan the whole source file instea dof just looking at the first few lines of a block.
I don't see what the value is of limiting the lifetime of the variable. The compiler isn't going to use that as a hint, anyway.
Not the compiler, but humans like me. I have just a small window of lines I can really focus on, and the smaller a block of code (including the needed variable declarations), the easier I get the impression I understand it.
It's just going to use this for syntax checking. If you define and initialize a variable at the top of the function, but don't use that variable until a hundred lines later, the compiler is going to initialize the variable when it's first used, not when the function is first entered. Chances are it's not even going to define stack space for it.
Keep in mind that we don't write the code for the compiler, but for the human being that comes after us and that has to maintain that code.
#ifdef CONFIG_COOL_FEATURE { u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks
} #endif
Is this an acceptable compromise?
This is what we do today, and I think it's ugly.
It is ugly, but much less ugly than variable declarations right in the middle of 200 lines of code.
Best regards,
Wolfgang Denk

Wolfgang Denk wrote:
Bear with an old man like me. I am used to the habit that variables get decleared at the begin of a block, not in the middle of it. When searching for the declaration of a variable, I find it a major PITA if I have to scan the whole source file instea dof just looking at the first few lines of a block.
This is why I use an advanced programmer's editor that brings me to the definition of the variable under the cursor with a single keystroke.
Not the compiler, but humans like me. I have just a small window of lines I can really focus on, and the smaller a block of code (including the needed variable declarations), the easier I get the impression I understand it.
In this case, it would be easier for you if the variable were declared next to the code that uses it.
This is what we do today, and I think it's ugly.
It is ugly, but much less ugly than variable declarations right in the middle of 200 lines of code.
This is where I disagree.

On Thu, Apr 9, 2009 at 7:38 AM, Timur Tabi timur@freescale.com wrote:
Wolfgang Denk wrote:
Bear with an old man like me. I am used to the habit that variables get decleared at the begin of a block, not in the middle of it. When searching for the declaration of a variable, I find it a major PITA if I have to scan the whole source file instea dof just looking at the first few lines of a block.
I'll second that
This is why I use an advanced programmer's editor that brings me to the definition of the variable under the cursor with a single keystroke.
What if _MY_ favourite editor doesn't. Or what if I don't have access to it because I'm looking at the code at work, or on a friends computer?
Not the compiler, but humans like me. I have just a small window of lines I can really focus on, and the smaller a block of code (including the needed variable declarations), the easier I get the impression I understand it.
That is the key - half the time #ifdef COOL_FEATURE in the middle of a function really means that the feature needs to be put in another function
In this case, it would be easier for you if the variable were declared next to the code that uses it.
True and correct, but it can often be done so in another function
This is what we do today, and I think it's ugly.
It is ugly, but much less ugly than variable declarations right in the middle of 200 lines of code.
200 lines of code is much more ugly
Regards,
Graeme

Graeme Russ wrote:
What if _MY_ favourite editor doesn't.
The point I'm trying to make is that I have tools at my disposal that make certain tasks easier for me, allowing me to alter my coding style and get the best of both worlds.
Or what if I don't have access to it because I'm looking at the code at work, or on a friends computer?
Then it will be more difficult for you. I have this problem sometimes. That's why I try to avoid using another tool as much as possible.
It's like complaining to someone who has a car that you only have a bicycle and you have to commute 20 miles to get to work. The person who has a car is obviously going to tell you that your life will be easier if you get a car also.

Dear Timur Tabi,
In message 49DD290A.9010306@freescale.com you wrote:
It's like complaining to someone who has a car that you only have a bicycle and you have to commute 20 miles to get to work. The person who has a car is obviously going to tell you that your life will be easier if you get a car also.
The person with the bicycle might ask you why you require him to contribute to air pollution and climate changes and all these things when you could as well put the target he has to reach just 200 meters from his home. Not everything that can be done is a good thing to do.
Best regards,
Wolfgang Denk

Wolfgang Denk wrote:
Dear Timur Tabi,
In message 49DD290A.9010306@freescale.com you wrote:
It's like complaining to someone who has a car that you only have a bicycle and you have to commute 20 miles to get to work. The person who has a car is obviously going to tell you that your life will be easier if you get a car also.
The person with the bicycle might ask you why you require him to contribute to air pollution and climate changes and all these things when you could as well put the target he has to reach just 200 meters from his home. Not everything that can be done is a good thing to do.
Indeed, having the variable declaration close by to where it's used *does* make things easier. :-)
-Scott

Dear Jerry Van Baren,
In message 49DCFF1D.6080006@ge.com you wrote:
If I'm not confused, I've seen block-local u-boot variables, has the advantages of being more distinctive and limits the lifetime of the variable.
#ifdef CONFIG_COOL_FEATURE { u32 myvarrocks = foo * bar * bar;
gd->neato = myvarrocks
} #endif
Is this an acceptable compromise?
Yes, if really necessary, this can be done.
Best regards,
Wolfgang Denk

Kumar Gala wrote:
I was wondering if there was any reason we avoid C99 features in u- boot source.
Maybe the best reason is that the Linux kernel avoids them, and staying consistent with the Linux coding style saves a lot of time and headaches. IMO, this is worth the occasional clumsiness that results.
BTW, the Linux kernel does not avoid all C99 features. For example, it relies heavily on named initialization of structs. However, AFAICT, it shuns those C99 feature that originated in C++.
Best regards, Larry

Larry Johnson wrote:
Kumar Gala wrote:
I was wondering if there was any reason we avoid C99 features in u- boot source.
Maybe the best reason is that the Linux kernel avoids them,
Linux has a lot more inertia than a smaller project such as u-boot.
and staying consistent with the Linux coding style saves a lot of time and headaches. IMO, this is worth the occasional clumsiness that results.
Code seems to flow from Linux to u-boot more than the reverse -- I don't see much of a problem with being more permissive.
BTW, the Linux kernel does not avoid all C99 features. For example, it relies heavily on named initialization of structs. However, AFAICT, it shuns those C99 feature that originated in C++.
I suspect that has more to do with people's feelings toward C++ than any unbiased assessment of the merits of the features.
-Scott
participants (10)
-
Ben Warren
-
Graeme Russ
-
Jerry Van Baren
-
Kumar Gala
-
Kumar Gala
-
Larry Johnson
-
Premi, Sanjeev
-
Scott Wood
-
Timur Tabi
-
Wolfgang Denk