ISO/ IEC JTC1/SC22/WG14 N883

					Document Number: ISO/IEC WG14 N883

----------------------------------------------------------------------------
The UK panel recommends a NO vote on the FDIS.

In general the panel considers that the FDIS is as good as we're going to
get in a reasonable timescale. While there are a large number of places
that could be improved, most of these can be sorted out at a later date
through the TC mechanism.

However, we consider that there are two issues that are exceptions to
this rule. As explained under the headings "Urgency", any attempt to
correct them in a TC would simply make things worse. We consider them
important enough to delay completion of the Standard.



Issue 1 - integer types longer than long
========================================

Summary
=======
Require that size_t be no wider than unsigned long and ptrdiff_t be no
wider than signed long.

Urgency
=======
If this change is not made now, there will be a window of opportunity -
of at least two years - when implementations can make size_t be wider
than unsigned long. By the time any future Amendment is ready it will be
impractical to re-impose the restriction. If the change *is* made now,
it can always be relaxed if it becomes necessary.

Rationale
=========
Various types in the Standard are defined as integer types. Two of these
- - size_t and ptrdiff_t - are frequently manipulated and on many
implementations need to hold values of the same order as [un]signed
long. In C89 there are various programming idioms that involve these
types but also need a standard integer type. For example:

    printf ("%lu", (unsigned long) sizeof X);

or:

    int *P1, *P2;
    ... /* make P1 and P2 point into the same array */
    malloc (sizeof (int) * labs (P1 - P2));

If these types are allowed to become wider than long, these idioms will
stop working. More importantly, this might not happen when the code is
compiled but rather when large values first get used by a previously
working program. This is clearly a Quiet Change.

There do not appear to be any implementations which would be affected by
this proposal, and it eliminates the vast majority of potential problems
with these two types. While there are other types that theoretically
meet these criteria, such as sig_atomic_t, in practice they are unlikely
to be larger than long and no action is needed. There are also types in
POSIX and other standards, such as off_t, which are similarly affected,
but they are outside the scope of C9X; the recommended practice section
would assist them.

Changes
=======
Append a new paragraph to 7.18.3:

    The value of SIZE_MAX shall be no greater than that of ULONG_MAX.
    The absolute values of PTRDIFF_MIN and PTRDIFF_MAX shall be no
    greater than those of LONG_MIN and LONG_MAX respectively.

or change the first part of 7.17 paragraph 2 to:

    [#2] The types are
               ptrdiff_t
    which  is  the  signed  integer  type  of  the   result   of
    subtracting two pointers (the width of ptrdiff_t shall be no greater
    than that of signed long);
               size_t
    which  is  the  unsigned  integer  type of the result of the
    sizeof operator (the width of size_t shall be no greater than that
    of unsigned long);

or both (the changes are equivalent in effect).

Possibly also add the following paragraph somewhere (perhaps in
6.3.1.3):

    Recommended practice

    Implementations should provide a mode which will warn of conversions
    (including those involving an explicit cast) where:
    - the original value was taken from an object whose type is derived
      from a typedef defined in a header provided by the implementation;
    - that type has a conversion rank greater than that of signed long;
    - the result type has a conversion rank equal to that of signed long.
    (Headers provided by the implementation are not limited to those
     defined by this Standard, but explicitly excludes <stdint.h>.)


Issue 2 - change return type of certain <fenv.h> functions
==========================================================

Summary
=======
Change the return type of various functions in 7.6.2 from void to int so
that they can fail.

Urgency
=======
These functions are new in C9X. Once the function prototypes have been
published it will not be practical to change them. The only solution
will be to produce new parallel functions with a return value; because
of the way these functions are defined, this will involve significantly
more change than just that.

Rationale
=========
The functions in question are to do with the floating-point exception
and environment flags. The former will do as an example.

The wording of the FDIS assumes that either:
- - the implementation has full control over the flags, or
- - the implementation has no control over the flags.
In the first case it defines various FE_ macros such as FE_DIVBYZERO for
the flags. The Standard then assumes that it is always possible to set
or clear the flag or to raise the exception. In the second case the
macros are not defined and so there are no valid argument values for the
functions (other than zero).

However, there are implementations that can do some things with the
flags but not others. For example, it may be possible to raise
exceptions but not to clear flags. This case is not allowed in the
present draft.

The two alternative proposed changes are:
(2A) Change the return types of the functions to int. For now the
functions always return zero (success) but a later Amendment can alter
this. This is the minimum to "future-proof".
(2B) Change the definitions properly to allow them to fail. This is more
complex but solves the problem once and for all.

Option 2B contains an extra item to make fesetround more consistent with
the other changes. This change may be omitted if it will increase
consensus.

Changes
=======
Option A - placeholder change
- -----------------------------
For each of the following functions:

    feclearexcept
    fegetexceptflag
    feraiseexcept
    fesetexceptflag
    fegetenv
    fesetenv
    feupdateenv

change the return type to int and add the following:

    Returns

    This function always returns zero. [*]

    [*] This may change in a future revision of this Standard, in which
    case a zero return will mean success and a non-zero return will mean
    failure of some kind.

Add to the Future Directions clause:

    The fact that various functions in 7.6.2 and 7.6.4 always return
    zero is an obsolescent feature.

Option B - full change
- ----------------------
In 7.6 paragraph 5, attach a footnote to the wording:

    if and only if the  implementation  supports  the
    floating-point exception by means of the functions in 7.6.2.

where the footnote is:

    [*] The implementation supports an exception if there are
    circumstances where a call to at least one of the functions in
    7.6.2, using the macro as the appropriate argument, will succeed. It
    is not necessary for all the functions to succeed all the time.

For each of the following functions:

    feclearexcept
    fegetexceptflag
    feraiseexcept
    fesetexceptflag
    fegetenv
    fesetenv
    feupdateenv

make changes equivalent to the following (which shows the wording
changes for 7.6.2.1).

In paragraph 2, replace "clears" with "attempt to clear".

Add a new heading and paragraph 3:

    Returns

    [3] The feclearexcept function returns zero if the excepts argument
    is zero or if all the specified exceptions were successfully
    cleared. Otherwise it returns a nonzero value.

Optional additional change: replace 7.6.3.2p3 by:

    [3] The fesetround function returns zero if and only if the requested
    rounding direction was established.

==== END ====