473,401 Members | 2,068 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,401 software developers and data experts.

what does macro "USE_VAR" used for?

Hi all, I found a macro "USE_VAR" in the code of bash-3.2 as
follows:
/*file: bash-3.2/shell.c*/
344 USE_VAR(argc);
345 USE_VAR(argv);
346 USE_VAR(env);
347 USE_VAR(code);
348 USE_VAR(old_errexit_flag);
349 #if defined (RESTRICTED_SHELL)
350 USE_VAR(saverst);

I found the definition of this macro at file shell.h as follows:

116 /* Force gcc to not clobber X on a longjmp(). Old versions of gcc
mangle
117 this badly. */
118 #if (__GNUC__ 2) || (__GNUC__ == 2 && __GNUC_MINOR__ 8)
119 # define USE_VAR(x) ((void) &(x))
120 #else
121 # define USE_VAR(x)
122 #endif
I think these code doesn't do anything really , it just control the
process of compilation. But how does it works? If the "else"
condition in file shell.h is true, the lines 344~350 in shell.c would
turn into "; ; ; ; ;".But what would happen in another condition?
Thanx!
Jul 18 '08 #1
4 2086
Gestorm wrote:
Hi all, I found a macro "USE_VAR" in the code of bash-3.2 as
follows:
/*file: bash-3.2/shell.c*/
344 USE_VAR(argc);
345 USE_VAR(argv);
346 USE_VAR(env);
347 USE_VAR(code);
348 USE_VAR(old_errexit_flag);
349 #if defined (RESTRICTED_SHELL)
350 USE_VAR(saverst);

I found the definition of this macro at file shell.h as follows:

116 /* Force gcc to not clobber X on a longjmp(). Old versions of gcc
mangle
117 this badly. */
118 #if (__GNUC__ 2) || (__GNUC__ == 2 && __GNUC_MINOR__ 8)
119 # define USE_VAR(x) ((void) &(x))
120 #else
121 # define USE_VAR(x)
122 #endif
I think these code doesn't do anything really , it just control the
process of compilation. But how does it works? If the "else"
condition in file shell.h is true, the lines 344~350 in shell.c would
turn into "; ; ; ; ;".But what would happen in another condition?
Thanx!
It's a trick that makes sure the compiler sees that a variable is "used"
even if it's not and therefore doesn't optimize it out or warn about a
possible coding error.

S
Jul 18 '08 #2
On Jul 18, 1:17 pm, Stephen Sprunk <step...@sprunk.orgwrote:
It's a trick that makes sure the compiler sees that a variable is "used"
even if it's not and therefore doesn't optimize it out or warn about a
possible coding error.
Thank you. But why does it use such a strange form? If I do this
#define USE_VAR(X) &(X)
would there be anything wrong?

Jul 18 '08 #3
Gestorm wrote:
>
On Jul 18, 1:17 pm, Stephen Sprunk <step...@sprunk.orgwrote:
It's a trick that makes sure the compiler sees that a variable is "used"
even if it's not and therefore doesn't optimize it out or warn about a
possible coding error.
Thank you. But why does it use such a strange form? If I do this
#define USE_VAR(X) &(X)
would there be anything wrong?
[...Original code had: # define USE_VAR(x) ((void) &(x)) ...]

That might give you a different warning about taking the address of
the variable and not doing anything about it. By casting the address
to void, you explicitly tell the compiler "yes, I know I'm throwing
out the result".

--
+-------------------------+--------------------+-----------------------+
| Kenneth J. Brody | www.hvcomputer.com | #include |
| kenbrody/at\spamcop.net | www.fptech.com | <std_disclaimer.h|
+-------------------------+--------------------+-----------------------+
Don't e-mail me at: <mailto:Th*************@gmail.com>

Jul 18 '08 #4
In article <95**********************************@z16g2000prn. googlegroups.com>
Gestorm <zh********@126.comwrote:
>Hi all, I found a macro "USE_VAR" in the code of bash-3.2 as
follows:
/*file: bash-3.2/shell.c*/
344 USE_VAR(argc);
345 USE_VAR(argv);
346 USE_VAR(env);
347 USE_VAR(code);
348 USE_VAR(old_errexit_flag);
349 #if defined (RESTRICTED_SHELL)
350 USE_VAR(saverst);

I found the definition of this macro at file shell.h as follows:

116 /* Force gcc to not clobber X on a longjmp(). Old versions of gcc
mangle
117 this badly. */
118 #if (__GNUC__ 2) || (__GNUC__ == 2 && __GNUC_MINOR__ 8)
119 # define USE_VAR(x) ((void) &(x))
120 #else
121 # define USE_VAR(x)
122 #endif

I think these code doesn't do anything really , it just control the
process of compilation. But how does it works?
It does not (work, that is).

Read the comment:

Force gcc to not clobber X on a longjmp().

Look up setjmp() and longjmp() in your C reference. These are
macros that "act like" a kind of goto, in which a setjmp() is a
goto label target, and a longjmp() will go to that label. If your
C reference is a good one, it will mention certain restrictions on
using local variables in functions that are the targets of these
longjmp "go to"s.

In normal ordinary C, you might write something like:

void somefunc(T1 parm1, T2 parm2) {
T3 localvar = initial_value;

top:
... do various things ...
use(parm1);
if (some condition) {
... maybe change localvar and/or parm1 and/or parm2 ...
use(parm2);
use(localvar);
if (some other condition)
goto top;
... maybe change localvar and/or parm1 and/or parm2 ...
if (some third condition)
goto top;
...
}
...
}

This kind of "goto", built into the language, is only mildly bad,
as it can only "go" within one particular function, in this case
the function named somefunc(). If you do go back to the label
"top", the local variable localvar and the parameters parm1 and
parm2 hold the new values set by any assignments or adjustments,
and uses of them will see the new values.

But suppose, for some reason, you want to be able to "go to" the
label "top" from a function that somefunc() calls, even indirectly,
without having to return through all the call layers. That is,
somefunc() calls a(), and a() calls b(), and b() calls c() which
calls d() which calls e() and so on up to z(), and then deep inside
of z() you decide you should "goto top" without ever returning from
z() or y() or x() or w() or ... all the way back to a(). You *can*
do this in C, using setjmp() and longjmp(). This is the kind of
goto you should strive mightily to avoid. The "mild" goto using
the "goto" keyword is bad enough, but this kind of goto is *terrible*.
(It is a bit like an exception in C++ except that it cannot even
be caught. This means that none of a() through y() ever have a
chance to do any clean up work -- close files, free memory, etc.
-- that they might need to do. It is possible, though difficult,
to build a "better" exception-like system that *does* have an
unwind-protect, using setjmp and longjmp in a stackable fashion,
but there are pitfalls.)

Now, the biggest problem with setjmp() and longjmp() is simply their
existence at all -- but if you *do* use them, they have another
problem. You, the C programmer, must add a "volatile" qualifier
to your parameter and local variables (not in absolutely all
cases, but in enough that you might as well just add it everywhere).
That is, if you want to rewrite somefunc() to allow a longjmp to
start over at "top", you must do this:

#include <setjmp.h>

jmp_buf label_top;

void somefunc(volatile T1 parm1, volatile T2 parm2) {
volatile T3 localvar = initial_value;

setjmp(label_top);
/*
* At any point, including in functions somefunc() calls,
* you can:
* longjmp(label_top);
* to "go to" "just after" the setjmp() macro, i.e., right
* here. This is like using a label like "top:" and doing
* a "goto top", except that because label_top is a "global
* variable" of type jmp_buf, it can be goto-ed from anywhere
* in the program, not just here in somefunc().
*/
... do your same various things, tests, etc ...
}

But note these "volatile" keywords I added. They are NOT OPTIONAL
(except in certain obscure circumstances).

Whoever wrote bash-3.2/shell.c did not realize this and did not
put in the correct "volatile"s. They then thought that gcc had a
bug, and put in even more code to attempt to "trick" the compiler
into behavior as if they had written correct code in the first
place. (As it happens, some versions of gcc *do* have a bug, even
if you use the "volatile" keyword as required. But that is not
what is going on here.)

The best fix for this problem is to avoid setjmp() and longjmp()
entirely. The second-best fix is to put in the required "volatile"s.
The USE_VAR macro is a hack, and is wrong and should be removed.
--
In-Real-Life: Chris Torek, Wind River Systems
Salt Lake City, UT, USA (40°39.22'N, 111°50.29'W) +1 801 277 2603
email: gmail (figure it out) http://web.torek.net/torek/index.html
Jul 20 '08 #5

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

11
by: becte | last post by:
What does the standard say about f(x++) ? 1. x is incremented and then the that value is used in function f, i.e. x++; f(x); 2. the value of x (before ++) is send to f and after returning. x is...
4
by: Garry Freemyer | last post by:
I'm trying to convert this macro to a c# function but I have a big problem. It's on the LEFT side of an assignment statement and I am extremely flustered over this one because I'm a little rusty...
7
by: Jake Thompson | last post by:
What does SIMENTRY mean as in ULONG SIMENTRY RemoveFolderItem( hSession, pszFolderID, pszItemID, pAsyncCtl, pRC ) is it necessary?
21
by: Niu Xiao | last post by:
I see a lot of use in function declarations, such as size_t fread(void* restrict ptr, size_t size, size_t nobj, FILE* restrict fp); but what does the keyword 'restrict' mean? there is no...
10
by: Thierry Lam | last post by:
What does the following macro mean, especially the << sign: #define hello(x) (( int64 ) floor( (double) x ) << 32) Thanks Thierry
6
by: raghu | last post by:
Hello This is raghu. And I want to know about the meaning of the statement given below log_txt( __FILE__, __LINE__, ##argList); in above statement what does FILE ,LINE ##argList mean. I want to...
45
by: loudking | last post by:
Hello, all I don't quite understand what does ((time_t)-1) mean when I execute "man 2 time" RETURN VALUE On success, the value of time in seconds since the Epoch is retu rned. On error,...
13
by: bobby | last post by:
hello group, what does for( ; ; ) mean in C program Thanks
3
by: qianz99 | last post by:
Hi I am not sure what this code does. I have the following questions 1. where is the case? 2. #define TLV_INTEGER(name, octets) p->name = -1; Is it define a function TLV_INTEGER(name, octets) ...
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows...
0
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...
0
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.