Arithmetic and C

Discussion in 'C Programming' started by Massimiliano Alberti, Mar 3, 2004.

  1. Are there rules on how should the C behave with the arithmetic operations?
    Are the overflows always ignored? And are they simply truncated? (if I have
    a 16-bits unsigned short ints
    unsigned short int a = 65535, b = 10; is a + b defined? And a * b? and b -
    a?)

    bye
    Massimiliano Alberti, Mar 3, 2004
    #1
    1. Advertising

  2. Massimiliano Alberti

    pete Guest

    Massimiliano Alberti wrote:
    >
    > Are there rules on how should
    > the C behave with the arithmetic operations?


    Yes.

    > Are the overflows always ignored? And are they simply truncated?'


    unsigned arithmetic is like that.

    > (if I have a 16-bits unsigned short ints
    > unsigned short int a = 65535, b = 10; is a + b defined?
    > And a * b? and b - a?)


    The complicated part about unsigned short, is that it is
    subject to the "usual arithmetic conversions" in arithmetic
    operations, and you don't know what type it promotes to.
    If int can represent all of the values of unsigned short,
    then unsigned short gets promoted to int,
    (overflow is undefined for signed types like int)
    otherwise it would get promoted to unsigned.

    --
    pete
    pete, Mar 3, 2004
    #2
    1. Advertising

  3. > The complicated part about unsigned short, is that it is
    > subject to the "usual arithmetic conversions" in arithmetic
    > operations, and you don't know what type it promotes to.
    > If int can represent all of the values of unsigned short,
    > then unsigned short gets promoted to int,
    > (overflow is undefined for signed types like int)
    > otherwise it would get promoted to unsigned.

    But there can't be an overflow if you promote two unsigned shorts to a
    (bigger) int... and if the int isn't bigger then the shorts won't be
    promoted (I think) (it would be pointless).

    --- bye
    Massimiliano Alberti, Mar 3, 2004
    #3
  4. Massimiliano Alberti

    pete Guest

    Massimiliano Alberti wrote:
    >
    > > The complicated part about unsigned short, is that it is
    > > subject to the "usual arithmetic conversions" in arithmetic
    > > operations, and you don't know what type it promotes to.
    > > If int can represent all of the values of unsigned short,
    > > then unsigned short gets promoted to int,
    > > (overflow is undefined for signed types like int)
    > > otherwise it would get promoted to unsigned.

    > But there can't be an overflow if you promote two unsigned shorts to a
    > (bigger) int... and if the int isn't bigger then the shorts won't be
    > promoted (I think) (it would be pointless).


    If two unsigned short values are converted to type int,
    and one value is INT_MAX and the other is 10,
    then the sum of those two int values, is undefined.

    --
    pete
    pete, Mar 3, 2004
    #4
  5. > If two unsigned short values are converted to type int,
    > and one value is INT_MAX and the other is 10,
    > then the sum of those two int values, is undefined.

    If the two unsigned short values are short values, how can they be INT_MAX?
    They are SHORT! They can be at max USHORT_MAX!

    --- bye
    Massimiliano Alberti, Mar 3, 2004
    #5
  6. "Massimiliano Alberti" <> writes:

    > Are there rules on how should the C behave with the arithmetic operations?
    > Are the overflows always ignored? And are they simply truncated? (if I have
    > a 16-bits unsigned short ints
    > unsigned short int a = 65535, b = 10; is a + b defined? And a * b? and b -
    > a?)


    Unsigned integers have "wrap-around" semantics, i.e. the result is
    reduced modulo the maximum value plus one. If USHRT_MAX is 65535 on
    your system, the following program fragment

    unsigned short int a = 65535, b = 10;
    unsigned short c = a + b;
    unsigned short d = a * b;
    unsigned short e = b - a;

    would cause c, d, e to be 9, 65526, 11, respectively. Note that due to
    integer promotions, the result of the /expression/ a + b could well be
    65545, if that number can be represented by type int.

    Overflowing signed integers causes undefined behavior.

    Martin


    --
    ,--. Martin Dickopp, Dresden, Germany ,= ,-_-. =.
    / ,- ) http://www.zero-based.org/ ((_/)o o(\_))
    \ `-' `-'(. .)`-'
    `-. Debian, a variant of the GNU operating system. \_/
    Martin Dickopp, Mar 3, 2004
    #6
  7. Massimiliano Alberti

    pete Guest

    Massimiliano Alberti wrote:
    >
    > > If two unsigned short values are converted to type int,
    > > and one value is INT_MAX and the other is 10,
    > > then the sum of those two int values, is undefined.

    > If the two unsigned short values are short values,
    > how can they be INT_MAX?
    > They are SHORT! They can be at max USHORT_MAX!


    CHAR_BIT equals 16
    sizeof(short) equals 1
    USHRT_MAX equals 65535
    sizeof(int) equals 2
    INT_MAX equals 65535
    INT_MIN equals -65535

    --
    pete
    pete, Mar 3, 2004
    #7
  8. Massimiliano Alberti

    Dan Pop Guest

    In <> pete <> writes:

    >Massimiliano Alberti wrote:
    >>
    >> Are there rules on how should
    >> the C behave with the arithmetic operations?

    >
    >Yes.
    >
    >> Are the overflows always ignored? And are they simply truncated?'

    >
    >unsigned arithmetic is like that.
    >
    >> (if I have a 16-bits unsigned short ints
    >> unsigned short int a = 65535, b = 10; is a + b defined?
    >> And a * b? and b - a?)

    >
    >The complicated part about unsigned short, is that it is
    >subject to the "usual arithmetic conversions" in arithmetic
    >operations, and you don't know what type it promotes to.
    >If int can represent all of the values of unsigned short,
    >then unsigned short gets promoted to int,
    >(overflow is undefined for signed types like int)


    However, overflow is very unlikely to happen from a + b, if a and b
    get promoted to int. INT_MAX == 65535 and USHRT_MAX == 65535 is
    theoretically possible, but very wasteful in practice.

    >otherwise it would get promoted to unsigned.


    And this is a good reason to avoid unsigned shorts, unless you have a
    compelling reason for using them.

    Dan
    --
    Dan Pop
    DESY Zeuthen, RZ group
    Email:
    Dan Pop, Mar 3, 2004
    #8
  9. Massimiliano Alberti

    Dan Pop Guest

    In <RWk1c.8412$> "Massimiliano Alberti" <> writes:

    >Are there rules on how should the C behave with the arithmetic operations?


    Signed arithmetic overflow causes undefined behaviour. Unsigned
    arithmetic overflow causes the result to be reduced modulo the largest
    representable value plus one. However, due to the integral promotions,
    arithmetic between unsigned operands shorter than unsigned int may be
    performed using signed int arithmetic.

    >Are the overflows always ignored? And are they simply truncated? (if I have
    >a 16-bits unsigned short ints
    >unsigned short int a = 65535, b = 10; is a + b defined? And a * b? and b -
    >a?)


    All of them are (normally) defined, but not *well* defined, because the
    result depends on the type of a and b *after* the integral promotions.
    If unsigned short is a 16-bit type, there are two *likely* scenarios:

    1. int is a 32-bit type, and then the results have type int and the values
    65545, 655350 and -65525, respectively.

    2. int is a 16-bit type, in which case the operands are promoted to
    unsigned int, which is a 16-bit type, too. In this case, the results
    have type unsigned int and the values 9, 65526 and 11, respectively.

    One can also imagine "exotic" scenarios where these operations generate
    signed integer overflow or yield unsigned results other than those
    mentioned above, but these are highly unlikely to occur in practice
    (that's why I called them "exotic").

    So, if you want consistent results, avoid using unsigned short operands.

    Dan
    --
    Dan Pop
    DESY Zeuthen, RZ group
    Email:
    Dan Pop, Mar 3, 2004
    #9
  10. Massimiliano Alberti

    Jack Klein Guest

    On Wed, 03 Mar 2004 14:07:26 GMT, pete <> wrote
    in comp.lang.c:

    > Massimiliano Alberti wrote:
    > >
    > > > If two unsigned short values are converted to type int,
    > > > and one value is INT_MAX and the other is 10,
    > > > then the sum of those two int values, is undefined.

    > > If the two unsigned short values are short values,
    > > how can they be INT_MAX?
    > > They are SHORT! They can be at max USHORT_MAX!

    >
    > CHAR_BIT equals 16
    > sizeof(short) equals 1
    > USHRT_MAX equals 65535
    > sizeof(int) equals 2
    > INT_MAX equals 65535
    > INT_MIN equals -65535


    ....all of which is a nice example of comp.lang.c pedantry, but I
    guarantee you no such implementation exists. Or likely ever will.

    --
    Jack Klein
    Home: http://JK-Technology.Com
    FAQs for
    comp.lang.c http://www.eskimo.com/~scs/C-faq/top.html
    comp.lang.c++ http://www.parashift.com/c -faq-lite/
    alt.comp.lang.learn.c-c++
    http://www.contrib.andrew.cmu.edu/~ajo/docs/FAQ-acllc.html
    Jack Klein, Mar 4, 2004
    #10
  11. Massimiliano Alberti

    Old Wolf Guest

    > >unsigned arithmetic is like that.
    > >
    > >> (if I have a 16-bits unsigned short ints
    > >> unsigned short int a = 65535, b = 10; is a + b defined?
    > >> And a * b? and b - a?)

    > >
    > >The complicated part about unsigned short, is that it is
    > >subject to the "usual arithmetic conversions" in arithmetic
    > >operations, and you don't know what type it promotes to.
    > >If int can represent all of the values of unsigned short,
    > >then unsigned short gets promoted to int,
    > >(overflow is undefined for signed types like int)

    >
    > However, overflow is very unlikely to happen from a + b, if a and b
    > get promoted to int. INT_MAX == 65535 and USHRT_MAX == 65535 is
    > theoretically possible, but very wasteful in practice.


    Borland/Turbo C for DOS, among others, has INT_MAX == 32767
    and USHRT_MAX == 65535. I think this means that:
    unsigned short s = 32767 + 10;
    is UB (the constants are signed ints), but
    unsigned short t = 32768 + 10;
    is not (32768 is signed long, and 10 gets promoted to match).
    Old Wolf, Mar 5, 2004
    #11
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. John Doe
    Replies:
    0
    Views:
    529
    John Doe
    Apr 17, 2005
  2. =?ISO-8859-1?Q?Christian_Brechb=FChler?=

    Arithmetic conversions/promotion and templates

    =?ISO-8859-1?Q?Christian_Brechb=FChler?=, Oct 19, 2003, in forum: C++
    Replies:
    3
    Views:
    418
    =?ISO-8859-1?Q?Christian_Brechb=FChler?=
    Oct 20, 2003
  3. Steven Bethard
    Replies:
    7
    Views:
    395
    Rocco Moretti
    Jan 20, 2006
  4. Xiangliang Meng
    Replies:
    2
    Views:
    247
    Keith Thompson
    Jul 23, 2004
  5. joshc
    Replies:
    5
    Views:
    552
    Keith Thompson
    Mar 31, 2005
Loading...

Share This Page