Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > Is this a legal way to use setjmp ?

Reply
Thread Tools

Is this a legal way to use setjmp ?

 
 
Spiros Bousbouras
Guest
Posts: n/a
 
      06-21-2007
In the following assume that a is int and
env is of type jmp_buf
a = setjmp(env) ;

Is it legal ? It looks reasonable but it seems to
violate what is mentioned under "Environmental
limits" of 7.13.1.1 of n869 so my guess is that
it's not legal.

If it's not legal could someone give me some insight
on why making this behave correctly would present
difficult problems for an implementation ?

 
Reply With Quote
 
 
 
 
Ben Pfaff
Guest
Posts: n/a
 
      06-21-2007
Spiros Bousbouras <(E-Mail Removed)> writes:

> In the following assume that a is int and
> env is of type jmp_buf
> a = setjmp(env) ;
> Is it legal ? It looks reasonable but it seems to
> violate what is mentioned under "Environmental
> limits" of 7.13.1.1 of n869 so my guess is that
> it's not legal.


No.

> If it's not legal could someone give me some insight
> on why making this behave correctly would present
> difficult problems for an implementation ?


The C99 rationale has this to say:

7.13.1.1 The setjmp macro

setjmp is constrained to be a macro only: in some
implementations the information necessary to restore context
is only available while executing the function making the
call to setjmp.

One proposed requirement on setjmp is that it be usable like
any other function, that is, that it be callable in any
expression context, and that the expression evaluate
correctly whether the return from setjmp is direct or via a
call to longjmp. Unfortunately, any implementation of setjmp
as a conventional called function cannot know enough about
the calling environment to save any temporary registers or
dynamic stack locations used part way through an expression
evaluation. (A setjmp macro seems to help only if it expands
to inline assembly code or a call to a special built- in
function.) The temporaries may be correct on the initial
call to setjmp, but are not likely to be on any return
initiated by a corresponding call to longjmp. These
considerations dictated the constraint that setjmp be called
only from within fairly simple expressions, ones not likely
to need temporary storage.

An alternative proposal considered by the C89 Committee was
to require that implementations recognize that calling setjmp
is a special case7, and hence that they take whatever
precautions are necessary to restore the setjmp environment
properly upon a longjmp call. This proposal was rejected on
grounds of consistency: implementations are currently allowed
to implement library functions specially, but no other
situations require special treatment.

--
Comp-sci PhD expected before end of 2007
Seeking industrial or academic position *outside California* in 2008
 
Reply With Quote
 
 
 
 
Spiros Bousbouras
Guest
Posts: n/a
 
      06-21-2007
On 21 Jun, 07:06, Ben Pfaff <(E-Mail Removed)> wrote:
> Spiros Bousbouras <(E-Mail Removed)> writes:
> > In the following assume that a is int and
> > env is of type jmp_buf
> > a = setjmp(env) ;
> > Is it legal ? It looks reasonable but it seems to
> > violate what is mentioned under "Environmental
> > limits" of 7.13.1.1 of n869 so my guess is that
> > it's not legal.

>
> No.
>
> > If it's not legal could someone give me some insight
> > on why making this behave correctly would present
> > difficult problems for an implementation ?

>
> The C99 rationale has this to say:

<snip>

I had read the relevant part of the rationale before posting
my question. What I'm looking for is a more concrete
explanation regarding the specific example I posted.


 
Reply With Quote
 
Spiros Bousbouras
Guest
Posts: n/a
 
      06-21-2007
On 21 Jun, 07:06, Ben Pfaff <(E-Mail Removed)> wrote:
> Spiros Bousbouras <(E-Mail Removed)> writes:
> > In the following assume that a is int and
> > env is of type jmp_buf
> > a = setjmp(env) ;
> > Is it legal ? It looks reasonable but it seems to
> > violate what is mentioned under "Environmental
> > limits" of 7.13.1.1 of n869 so my guess is that
> > it's not legal.

>
> No.
>
> > If it's not legal could someone give me some insight
> > on why making this behave correctly would present
> > difficult problems for an implementation ?

>
> The C99 rationale has this to say:
>
> 7.13.1.1 The setjmp macro


< partial snip>

> An alternative proposal considered by the C89 Committee was
> to require that implementations recognize that calling setjmp
> is a special case7, and hence that they take whatever
> precautions are necessary to restore the setjmp environment
> properly upon a longjmp call. This proposal was rejected on
> grounds of consistency: implementations are currently allowed
> to implement library functions specially, but no other
> situations require special treatment.


It occurs to me that not allowing something as basic as
a = setjmp(env) ;
is not very consistent either. Are there other examples of functions
or macros where you cannot do that ?

 
Reply With Quote
 
Richard Tobin
Guest
Posts: n/a
 
      06-21-2007
In article <(E-Mail Removed) .com>,
Spiros Bousbouras <(E-Mail Removed)> wrote:

>In the following assume that a is int and
>env is of type jmp_buf
>a = setjmp(env) ;
>
>Is it legal ? It looks reasonable but it seems to
>violate what is mentioned under "Environmental
>limits" of 7.13.1.1 of n869 so my guess is that
>it's not legal.
>
>If it's not legal could someone give me some insight
>on why making this behave correctly would present
>difficult problems for an implementation ?


When longjmp() is called control will return to the calling function
in the middle of the expression a=setjmp(env). In general, that
expression might use arbitrary temporary registers, but if
setjmp() is an ordinary function it will not be able to determine
which registers those are.

I don't find this entirely convincing - setjmp() could just save all
the registers used as temporaries, and if that's too expensive then
you don't *have* to implement it as an ordinary function, and in any
case how many unknown temporaries are going to be used in a simple
assignment? - but then I've never written a C compiler.

Perhaps there were existing implementations that couldn't handle it.
No-one designing a new language would expect to be able to implement
something like setjmp() as a plain function.

-- Richartd
--
"Consideration shall be given to the need for as many as 32 characters
in some alphabets" - X3.4, 1963.
 
Reply With Quote
 
Chris Torek
Guest
Posts: n/a
 
      06-23-2007
>>Spiros Bousbouras <(E-Mail Removed)> writes:
[given appropriate definitions of a and env]
>>>a = setjmp(env); ... seems to violate [a non-"constraint" "shall"]
>>>limits" of 7.13.1.1 of n869 so my guess is that it's not legal.


Indeed, code of this form uses undefined (at least undefined-
by-the-C-standards) behavior.

In article <(E-Mail Removed) .com>
Spiros Bousbouras <(E-Mail Removed)> wrote:
>I had read the relevant part of the rationale before posting
>my question. What I'm looking for is a more concrete
>explanation regarding the specific example I posted.


It is somewhat (or even "very" ) difficult to come up with
a good example of how things go wrong here. What it boils down
to, in some sense, is a reluctance to force implementations to
recognize that "setjmp" is not a normal function.

On most machines, control flow tends to involve pushes and
pops onto a stack. This stack may or may not be shared with
that for arguments and/or function return values. When
evaluating complex expressions, this same stack may also be
used by the compiler for compiler-temporaries.

If the compiler believes that setjmp() is an ordinary function,
and therefore it has no "strange stack effects", the compiler
can interleave its own stack manipulations between those that
might occur for any ordinary function call. But if that same
stack is used for control flow, and setjmp() is "returned to"
by a later longjmp() so that control flow is abnormal, there
may be some sort of destructive interference between the two.

The same problem occurs with the (non-Standard) alloca()
function on machines like the x86. Since actual alloca()
implementations alter the stack, calls to alloca() must not
occur "between" operations that also alter the stack. Thus:

char *p;
size_t n;
...
p = alloca(n);

tends to work, but more complex operations like:

foo(p1 = alloca(n), bar(42), p2 = alloca(n), baz(p3 = alloca(n)));

tend to behave badly, because the compiler's stack adjustments
alter alloca()'s stack adjustments, so that p1, p2, and/or p3 may
point to the "wrong part" of the stack.

Simple assignments are likely to work even with "dumb" compilers
that implement setjmp() in the obvious, simple, way (without any
special-casing inside the compiler). More complex operations
like:

foo(setjmp(label1), 42, setjmp(label2));

are clearly asking for trouble. The fact is that setjmp() is like
a goto-label, and longjmp() actually goes to a setjmp() label, and
if a compiler recognizes these through special syntax -- in the
same way that any C99 compiler must now recognize the creation of
a variable-length array due to its special syntax[%] -- it can
arrange for the "right thing" to happen. A future Standard could
expand the list of "allowable setjmp situations" without really
harming anything, except perhaps compiler-writers' free time.

[% Admittedly, VLA syntax looks like any other array definition.
The compiler can "see" that it is a VLA, though, because the
expression(s) that create the dimensions are not compile-time
constant-expressions. The Standard -- either one -- could have
done effectively the same thing with setjmp and longjmp by declaring
that they are keywords, or at least macros that expand to keywords,
even though they *look* like ordinary function calls. The
standards-folk simply chose not to do that.]
--
In-Real-Life: Chris Torek, Wind River Systems
Salt Lake City, UT, USA (4039.22'N, 11150.29'W) +1 801 277 2603
email: forget about it http://web.torek.net/torek/index.html
Reading email is like searching for food in the garbage, thanks to spammers.
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Is this setjmp/jongjmp usable legal? Player C Programming 23 01-07-2013 05:02 AM
Is setjmp/longjmp ok? Michael B Allen C Programming 11 05-04-2004 08:57 PM
help: why setjmp/longjmp take STRUCT jmp_buf as parameter, not a pointer? someone C Programming 5 05-01-2004 02:47 AM
setjmp, longjmp Mantorok Redgormor C Programming 2 11-12-2003 04:59 PM
How dirty is setjmp+fopen+longjmp ? Thomas Baruchel C Programming 2 10-02-2003 04:56 PM



Advertisments