Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. The Lounge
  3. C++ integer arithmetic overflow

C++ integer arithmetic overflow

Scheduled Pinned Locked Moved The Lounge
c++question
25 Posts 19 Posters 1 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • N Nelek

    0x01AA wrote:

    I guess it's because I've finally grown up ;-P

    I would like to think than I have got younger... :laugh: :laugh:

    M.D.V. ;) If something has a solution... Why do we have to worry about?. If it has no solution... For what reason do we have to worry about? Help me to understand what I'm saying, and I'll explain it better to you Rating helpful answers is nice, but saying thanks can be even nicer.

    0 Offline
    0 Offline
    0x01AA
    wrote on last edited by
    #15

    No chance for us all to turn back the clock ;)

    1 Reply Last reply
    0
    • J JudyL_MD

      The usual way is after adding two positive numbers together, check if the result is negative. If it is, you've overflowed. You can also, if you're adding two 32-bit numbers together, cast them both to 64-bit, then add them and check if the resulting 64-bit value is greater than INT32_MAX. Judy

      Be wary of strong drink. It can make you shoot at tax collectors - and miss. Lazarus Long, "Time Enough For Love" by Robert A. Heinlein

      J Offline
      J Offline
      jmaida
      wrote on last edited by
      #16

      Many moons ago, I was called in as consultant for a small business using Cobol and random access files for recording inventory transactions. Their main database file had been corrupted with new transactions overwriting existing transactions. I suspected integer oveflow. The field in the header record for the file was used to store the next free location. It was 16 bits so once they reached 65536 transactions the next free location was previously used. The Cobol number field was always positive so the roll over just went backwards. They were very surprised that 65536 transactions had occured. The coding fix was easy. I had to calculate the corrupted locations and restore the data from backups. Because I was still in Grad school, and the owner provided me extra pay for less hours so I could finish. True story.

      "A little time, a little trouble, your better day" Badfinger

      1 Reply Last reply
      0
      • J JudyL_MD

        The usual way is after adding two positive numbers together, check if the result is negative. If it is, you've overflowed. You can also, if you're adding two 32-bit numbers together, cast them both to 64-bit, then add them and check if the resulting 64-bit value is greater than INT32_MAX. Judy

        Be wary of strong drink. It can make you shoot at tax collectors - and miss. Lazarus Long, "Time Enough For Love" by Robert A. Heinlein

        U Offline
        U Offline
        User 13269747
        wrote on last edited by
        #17

        Quote:

        The usual way is after adding two positive numbers together, check if the result is negative. If it is, you've overflowed.

        This doesn't work, because overflowing is undefined behaviour and the compiler is allowed to remove the check (i.e. it will never overflow). See this short snippet[^] The compiler completely removes the "overflow" path, so the check you propose *always* prints "Not overflowed".

        1 Reply Last reply
        0
        • B BernardIE5317

          may i inquire how C++ integer arithmetic is performed in your code so as to prevent / detect / report overflow ?

          U Offline
          U Offline
          User 13269747
          wrote on last edited by
          #18

          Quote:

          may i inquire how C++ integer arithmetic is performed in your code so as to prevent / detect / report overflow ?

          Determining overflow is not possible with signed integers (compiler is free to remove the check on signed integers, but has to keep the check for unsigned integers) so I try to use unsigned over signed wherever possible, and then I can check rollover using less-than/greater-than zero for overflow/underflow respectively. When I am forced to use signed (to interface to existing code), I use a larger integer than the interface specifies: use int16_t for 8 bit ints, int32_t for 16 bit ints, int64_t for 32 bit ints. For an interface that needs 64 bit ints I use the rollover/rollunder zero (using less-than and greater-than) after casting the signed 64 bit value to an unsigned 64 bit value. Under no circumstance is it safe to use plain `int` portably. All usage of plain `int` depends on the platform (hardware + compiler + OS combination), so you cannot write code that works now and in the future, you can only use the plain `int` type for code on a particular platform at a particular point in time - future versions of your platform have have a different sized `int`.

          J 1 Reply Last reply
          0
          • B BernardIE5317

            may i inquire how C++ integer arithmetic is performed in your code so as to prevent / detect / report overflow ?

            L Offline
            L Offline
            Lurk
            wrote on last edited by
            #19

            An ounce of prevention is worth a pound of cure. Take either addend and subtract it from the maximum. If the result is smaller than the other addend, you will overflow. If Max - A < B, then A + B > Max // OVERFLOW

            M 1 Reply Last reply
            0
            • U User 13269747

              Quote:

              may i inquire how C++ integer arithmetic is performed in your code so as to prevent / detect / report overflow ?

              Determining overflow is not possible with signed integers (compiler is free to remove the check on signed integers, but has to keep the check for unsigned integers) so I try to use unsigned over signed wherever possible, and then I can check rollover using less-than/greater-than zero for overflow/underflow respectively. When I am forced to use signed (to interface to existing code), I use a larger integer than the interface specifies: use int16_t for 8 bit ints, int32_t for 16 bit ints, int64_t for 32 bit ints. For an interface that needs 64 bit ints I use the rollover/rollunder zero (using less-than and greater-than) after casting the signed 64 bit value to an unsigned 64 bit value. Under no circumstance is it safe to use plain `int` portably. All usage of plain `int` depends on the platform (hardware + compiler + OS combination), so you cannot write code that works now and in the future, you can only use the plain `int` type for code on a particular platform at a particular point in time - future versions of your platform have have a different sized `int`.

              J Offline
              J Offline
              JSilvers
              wrote on last edited by
              #20

              Sorry for inadvertent click on inappropriate content

              Joan F Silverston jsilverston@cox.net nhswinc.com

              1 Reply Last reply
              0
              • J JudyL_MD

                The usual way is after adding two positive numbers together, check if the result is negative. If it is, you've overflowed. You can also, if you're adding two 32-bit numbers together, cast them both to 64-bit, then add them and check if the resulting 64-bit value is greater than INT32_MAX. Judy

                Be wary of strong drink. It can make you shoot at tax collectors - and miss. Lazarus Long, "Time Enough For Love" by Robert A. Heinlein

                M Offline
                M Offline
                Martijn Smitshoek
                wrote on last edited by
                #21

                As mentioned above, specifically undefined behavior might turn out in such a way that the "signed"ness does not necessarily flip as you would expect. Having said that, I don't know of a CPU/compiler that doesn't simply let the integers wrap around because that is still the easiest to implement. I was almost trying to propose some right-shift logic trick to check, but, the right-shift is, in fact, undefined for signed integers as well and may give invalid results. In assembly it's plain simple, you typically check the carry or overflow flag for unsigned or signed integers, respectively. Finally, a watertight solution would be to cut every integer in two halves using masks and shifts, then craft your own carry- and overflow logic. I'm too lazy to work it out in detail but I'm positive that all the information you need to detect overflow is in the high bits of the upper sum. Something like, upper half, or upper half + 1 bits must turn out equal, and if not, there is overflow.

                1 Reply Last reply
                0
                • L Lurk

                  An ounce of prevention is worth a pound of cure. Take either addend and subtract it from the maximum. If the result is smaller than the other addend, you will overflow. If Max - A < B, then A + B > Max // OVERFLOW

                  M Offline
                  M Offline
                  Martijn Smitshoek
                  wrote on last edited by
                  #22

                  Whether an ounce is more than a pound depends on foreign imperial units, and scales that might overflow. Having said that, the method is properly defined in C(++) for unsigned all integers, using each their respective maximums, and easier than what I proposed.

                  1 Reply Last reply
                  0
                  • B BernardIE5317

                    may i inquire how C++ integer arithmetic is performed in your code so as to prevent / detect / report overflow ?

                    D Offline
                    D Offline
                    David On Life
                    wrote on last edited by
                    #23

                    There's many discussions of this on many StackOverflow and other threads. Some compilers support options to [enable throwing exceptions on overflow](https://stackoverflow.com/questions/3679047/integer-overflow-in-c-standards-and-compilers) including GCC (-ftrapv) or checked intrinsic options. If you're willing to wait, the [C23 standard](https://www.open-std.org/jtc1/sc22/wg14/www/docs/n3047.pdf) includes a proposal for a stdckdint library with functions for performing checked integer math. Otherwise, you probably need to either find a 3rd party library that does this (or write your own methods where you can use one of many techniques depending on your performance requirements). Also, [C# supports checked expressions](https://stackoverflow.com/questions/2056445/no-overflow-exception-for-int-in-c) as either a compiler option or a local code block, in case that's an option.

                    B 1 Reply Last reply
                    0
                    • D David On Life

                      There's many discussions of this on many StackOverflow and other threads. Some compilers support options to [enable throwing exceptions on overflow](https://stackoverflow.com/questions/3679047/integer-overflow-in-c-standards-and-compilers) including GCC (-ftrapv) or checked intrinsic options. If you're willing to wait, the [C23 standard](https://www.open-std.org/jtc1/sc22/wg14/www/docs/n3047.pdf) includes a proposal for a stdckdint library with functions for performing checked integer math. Otherwise, you probably need to either find a 3rd party library that does this (or write your own methods where you can use one of many techniques depending on your performance requirements). Also, [C# supports checked expressions](https://stackoverflow.com/questions/2056445/no-overflow-exception-for-int-in-c) as either a compiler option or a local code block, in case that's an option.

                      B Offline
                      B Offline
                      BernardIE5317
                      wrote on last edited by
                      #24

                      i have written functions for addition and subtraction with signature

                      template requires integral&& integral&& integral
                      sumType addition(augendType augend, addendType addend, OPTIONAL\_MATH\_CLIMITS\_TYPE(sumType) limits =EMPTY\_OPTIONAL\_MATH\_CLIMITS(sumType));
                      

                      it ensures if the requested result type can store the result no overflow will result no matter the argument size or sign . also variadic forms . these variadic forms minimize the chance of overflow by rearranging the arguments exempli gratia MAXINT + MAXINT - MAXINT becomes MAXINT - MAXINT + MAXINT . i am considering writing a variadic function which accepts all the arithmetic operators as arguments and utilizes the above techniques . my original post was to discern if such would be usefol to others and to learn of other options for myself .

                      1 Reply Last reply
                      0
                      • B BernardIE5317

                        may i inquire how C++ integer arithmetic is performed in your code so as to prevent / detect / report overflow ?

                        _ Offline
                        _ Offline
                        __Tobias__
                        wrote on last edited by
                        #25

                        I would suggest having a look at the built-in functions of the compilers that feature an overflow check. According to this post most recent compilers (GCC, Clang, Intel, MSVC) provide them. Documentation: https://gcc.gnu.org/onlinedocs/gcc/Integer-Overflow-Builtins.html

                        bool __builtin_add_overflow (type1 a, type2 b, type3 *res)
                        bool __builtin_sub_overflow (type1 a, type2 b, type3 *res)
                        bool __builtin_mul_overflow (type1 a, type2 b, type3 *res)

                        bool __builtin_add_overflow_p (type1 a, type2 b, type3 c)
                        bool __builtin_sub_overflow_p (type1 a, type2 b, type3 c)
                        bool __builtin_mul_overflow_p (type1 a, type2 b, type3 c)

                        1 Reply Last reply
                        0
                        Reply
                        • Reply as topic
                        Log in to reply
                        • Oldest to Newest
                        • Newest to Oldest
                        • Most Votes


                        • Login

                        • Don't have an account? Register

                        • Login or register to search.
                        • First post
                          Last post
                        0
                        • Categories
                        • Recent
                        • Tags
                        • Popular
                        • World
                        • Users
                        • Groups